├── .gitignore
├── LICENSE
├── README.md
├── example
├── README.md
├── grpc
│ ├── bash
│ │ ├── build.sh
│ │ └── server.sh
│ ├── build
│ │ ├── proto
│ │ │ ├── Example_grpc_pb.d.ts
│ │ │ ├── Example_grpc_pb.js
│ │ │ ├── Example_pb.d.ts
│ │ │ └── Example_pb.js
│ │ ├── server.d.ts
│ │ ├── server.js
│ │ └── server.js.map
│ ├── package.json
│ ├── proto
│ │ └── Example.proto
│ ├── src
│ │ ├── proto
│ │ │ ├── Example_grpc_pb.d.ts
│ │ │ ├── Example_grpc_pb.js
│ │ │ ├── Example_pb.d.ts
│ │ │ └── Example_pb.js
│ │ └── server.ts
│ ├── tsconfig.json
│ ├── tslint.json
│ └── yarn.lock
├── index.js
├── package-lock.json
├── package.json
├── schema.graphql
└── yarn.lock
├── grpcgraphql.png
├── lib
├── index.d.ts
├── index.js
├── index.js.map
├── protobuf.d.ts
├── protobuf.js
├── protobuf.js.map
├── service_converter.d.ts
├── service_converter.js
├── service_converter.js.map
├── subscription.d.ts
├── subscription.js
├── subscription.js.map
├── type_converter.d.ts
├── type_converter.js
├── type_converter.js.map
├── types.d.ts
├── types.js
└── types.js.map
├── package-lock.json
├── package.json
├── src
├── index.ts
├── protobuf.ts
├── service_converter.ts
├── subscription.ts
├── type_converter.ts
├── types.ts
└── typings.d.ts
├── tsconfig.json
├── tslint.json
└── yarn.lock
/.gitignore:
--------------------------------------------------------------------------------
1 | # Logs
2 | logs
3 | *.log
4 | npm-debug.log*
5 | yarn-debug.log*
6 | yarn-error.log*
7 |
8 | # Runtime data
9 | pids
10 | *.pid
11 | *.seed
12 | *.pid.lock
13 |
14 | # Directory for instrumented libs generated by jscoverage/JSCover
15 | lib-cov
16 |
17 | # Coverage directory used by tools like istanbul
18 | coverage
19 |
20 | # nyc test coverage
21 | .nyc_output
22 |
23 | # Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files)
24 | .grunt
25 |
26 | # Bower dependency directory (https://bower.io/)
27 | bower_components
28 |
29 | # node-waf configuration
30 | .lock-wscript
31 |
32 | # Compiled binary addons (https://nodejs.org/api/addons.html)
33 | build/Release
34 |
35 | # Dependency directories
36 | node_modules/
37 | jspm_packages/
38 |
39 | # TypeScript v1 declaration files
40 | typings/
41 |
42 | # Optional npm cache directory
43 | .npm
44 |
45 | # Optional eslint cache
46 | .eslintcache
47 |
48 | # Optional REPL history
49 | .node_repl_history
50 |
51 | # Output of 'npm pack'
52 | *.tgz
53 |
54 | # Yarn Integrity file
55 | .yarn-integrity
56 |
57 | # dotenv environment variables file
58 | .env
59 |
60 | # next.js build output
61 | .next
62 |
63 | .DS_Store
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2019 Xanthous Tech
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # Grpc Graphql Schema
2 |
3 |
4 |
5 |
6 |
7 | Convert gRPC proto Definition into GraphQL Schema
8 |
9 | [Slides @ GraphQL BKK 4.0](https://docs.google.com/presentation/d/11sw3yK7p6xYcES9Wsjco7z3lGgmYlefnNrqhZ6vaYvA/edit?usp=sharing)
10 |
11 | [Medium Article](https://medium.com/xanthous/translating-grpc-services-into-graphql-6a8e49556d96)
12 |
13 | # How to Use
14 |
15 | ```javascript
16 | const { getGraphqlSchemaFromGrpc } = require('grpc-graphql-schema');
17 |
18 | getGraphqlSchemaFromGrpc({
19 | endpoint: 'localhost:50051',
20 | protoFilePath: '/path/to/ServiceDefinition.proto',
21 | serviceName: 'GrpcServiceName',
22 | packageName: 'name.package',
23 | }).then(schema => {
24 | // load schema in graphql server
25 | });
26 | ```
27 |
--------------------------------------------------------------------------------
/example/README.md:
--------------------------------------------------------------------------------
1 | # How to Run this Demo
2 |
3 | ```
4 | # start the gRPC server
5 | cd grpc
6 | npm install
7 | npm start
8 |
9 | # start the GraphQL server
10 | cd ..
11 | npm install
12 | npm start
13 | ```
--------------------------------------------------------------------------------
/example/grpc/bash/build.sh:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env bash
2 |
3 | BASEDIR=$(dirname "$0")
4 | cd ${BASEDIR}/../
5 |
6 | PROTO_DEST=./src/proto
7 |
8 | mkdir -p ${PROTO_DEST}
9 |
10 | # JavaScript code generating
11 | ./node_modules/.bin/grpc_tools_node_protoc \
12 | --js_out=import_style=commonjs,binary:${PROTO_DEST} \
13 | --grpc_out=${PROTO_DEST} \
14 | --plugin=protoc-gen-grpc=./node_modules/.bin/grpc_tools_node_protoc_plugin \
15 | -I ./proto \
16 | proto/*.proto
17 |
18 | ./node_modules/.bin/grpc_tools_node_protoc \
19 | --plugin=protoc-gen-ts=./node_modules/.bin/protoc-gen-ts \
20 | --ts_out=${PROTO_DEST} \
21 | -I ./proto \
22 | proto/*.proto
23 |
24 | # TypeScript compiling
25 | mkdir -p build/proto
26 | cp -r ./src/proto/* build/proto
27 | tsc
--------------------------------------------------------------------------------
/example/grpc/bash/server.sh:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env bash
2 |
3 | BASEDIR=$(dirname "$0")
4 | cd ${BASEDIR}/../
5 |
6 | DEBUG=* node ./build/server.js
--------------------------------------------------------------------------------
/example/grpc/build/proto/Example_grpc_pb.d.ts:
--------------------------------------------------------------------------------
1 | // package: io.xtech.example
2 | // file: Example.proto
3 |
4 | /* tslint:disable */
5 |
6 | import * as grpc from "grpc";
7 | import * as Example_pb from "./Example_pb";
8 |
9 | interface IExampleService extends grpc.ServiceDefinition {
10 | setMovies: IExampleService_ISetMovies;
11 | searchMoviesByCast: IExampleService_ISearchMoviesByCast;
12 | }
13 |
14 | interface IExampleService_ISetMovies extends grpc.MethodDefinition {
15 | path: string; // "/io.xtech.example.Example/SetMovies"
16 | requestStream: boolean; // false
17 | responseStream: boolean; // false
18 | requestSerialize: grpc.serialize;
19 | requestDeserialize: grpc.deserialize;
20 | responseSerialize: grpc.serialize;
21 | responseDeserialize: grpc.deserialize;
22 | }
23 | interface IExampleService_ISearchMoviesByCast extends grpc.MethodDefinition {
24 | path: string; // "/io.xtech.example.Example/SearchMoviesByCast"
25 | requestStream: boolean; // false
26 | responseStream: boolean; // true
27 | requestSerialize: grpc.serialize;
28 | requestDeserialize: grpc.deserialize;
29 | responseSerialize: grpc.serialize;
30 | responseDeserialize: grpc.deserialize;
31 | }
32 |
33 | export const ExampleService: IExampleService;
34 |
35 | export interface IExampleServer {
36 | setMovies: grpc.handleUnaryCall;
37 | searchMoviesByCast: grpc.handleServerStreamingCall;
38 | }
39 |
40 | export interface IExampleClient {
41 | setMovies(request: Example_pb.EmptyRequest, callback: (error: grpc.ServiceError | null, response: Example_pb.MoviesResult) => void): grpc.ClientUnaryCall;
42 | setMovies(request: Example_pb.EmptyRequest, metadata: grpc.Metadata, callback: (error: grpc.ServiceError | null, response: Example_pb.MoviesResult) => void): grpc.ClientUnaryCall;
43 | setMovies(request: Example_pb.EmptyRequest, metadata: grpc.Metadata, options: Partial, callback: (error: grpc.ServiceError | null, response: Example_pb.MoviesResult) => void): grpc.ClientUnaryCall;
44 | searchMoviesByCast(request: Example_pb.SearchByCastInput, options?: Partial): grpc.ClientReadableStream;
45 | searchMoviesByCast(request: Example_pb.SearchByCastInput, metadata?: grpc.Metadata, options?: Partial): grpc.ClientReadableStream;
46 | }
47 |
48 | export class ExampleClient extends grpc.Client implements IExampleClient {
49 | constructor(address: string, credentials: grpc.ChannelCredentials, options?: object);
50 | public setMovies(request: Example_pb.EmptyRequest, callback: (error: grpc.ServiceError | null, response: Example_pb.MoviesResult) => void): grpc.ClientUnaryCall;
51 | public setMovies(request: Example_pb.EmptyRequest, metadata: grpc.Metadata, callback: (error: grpc.ServiceError | null, response: Example_pb.MoviesResult) => void): grpc.ClientUnaryCall;
52 | public setMovies(request: Example_pb.EmptyRequest, metadata: grpc.Metadata, options: Partial, callback: (error: grpc.ServiceError | null, response: Example_pb.MoviesResult) => void): grpc.ClientUnaryCall;
53 | public searchMoviesByCast(request: Example_pb.SearchByCastInput, options?: Partial): grpc.ClientReadableStream;
54 | public searchMoviesByCast(request: Example_pb.SearchByCastInput, metadata?: grpc.Metadata, options?: Partial): grpc.ClientReadableStream;
55 | }
56 |
--------------------------------------------------------------------------------
/example/grpc/build/proto/Example_grpc_pb.js:
--------------------------------------------------------------------------------
1 | // GENERATED CODE -- DO NOT EDIT!
2 |
3 | 'use strict';
4 | var grpc = require('grpc');
5 | var Example_pb = require('./Example_pb.js');
6 |
7 | function serialize_io_xtech_example_EmptyRequest(arg) {
8 | if (!(arg instanceof Example_pb.EmptyRequest)) {
9 | throw new Error('Expected argument of type io.xtech.example.EmptyRequest');
10 | }
11 | return new Buffer(arg.serializeBinary());
12 | }
13 |
14 | function deserialize_io_xtech_example_EmptyRequest(buffer_arg) {
15 | return Example_pb.EmptyRequest.deserializeBinary(new Uint8Array(buffer_arg));
16 | }
17 |
18 | function serialize_io_xtech_example_Movie(arg) {
19 | if (!(arg instanceof Example_pb.Movie)) {
20 | throw new Error('Expected argument of type io.xtech.example.Movie');
21 | }
22 | return new Buffer(arg.serializeBinary());
23 | }
24 |
25 | function deserialize_io_xtech_example_Movie(buffer_arg) {
26 | return Example_pb.Movie.deserializeBinary(new Uint8Array(buffer_arg));
27 | }
28 |
29 | function serialize_io_xtech_example_MoviesResult(arg) {
30 | if (!(arg instanceof Example_pb.MoviesResult)) {
31 | throw new Error('Expected argument of type io.xtech.example.MoviesResult');
32 | }
33 | return new Buffer(arg.serializeBinary());
34 | }
35 |
36 | function deserialize_io_xtech_example_MoviesResult(buffer_arg) {
37 | return Example_pb.MoviesResult.deserializeBinary(new Uint8Array(buffer_arg));
38 | }
39 |
40 | function serialize_io_xtech_example_SearchByCastInput(arg) {
41 | if (!(arg instanceof Example_pb.SearchByCastInput)) {
42 | throw new Error('Expected argument of type io.xtech.example.SearchByCastInput');
43 | }
44 | return new Buffer(arg.serializeBinary());
45 | }
46 |
47 | function deserialize_io_xtech_example_SearchByCastInput(buffer_arg) {
48 | return Example_pb.SearchByCastInput.deserializeBinary(new Uint8Array(buffer_arg));
49 | }
50 |
51 |
52 | var ExampleService = exports.ExampleService = {
53 | setMovies: {
54 | path: '/io.xtech.example.Example/SetMovies',
55 | requestStream: false,
56 | responseStream: false,
57 | requestType: Example_pb.EmptyRequest,
58 | responseType: Example_pb.MoviesResult,
59 | requestSerialize: serialize_io_xtech_example_EmptyRequest,
60 | requestDeserialize: deserialize_io_xtech_example_EmptyRequest,
61 | responseSerialize: serialize_io_xtech_example_MoviesResult,
62 | responseDeserialize: deserialize_io_xtech_example_MoviesResult,
63 | },
64 | searchMoviesByCast: {
65 | path: '/io.xtech.example.Example/SearchMoviesByCast',
66 | requestStream: false,
67 | responseStream: true,
68 | requestType: Example_pb.SearchByCastInput,
69 | responseType: Example_pb.Movie,
70 | requestSerialize: serialize_io_xtech_example_SearchByCastInput,
71 | requestDeserialize: deserialize_io_xtech_example_SearchByCastInput,
72 | responseSerialize: serialize_io_xtech_example_Movie,
73 | responseDeserialize: deserialize_io_xtech_example_Movie,
74 | },
75 | };
76 |
77 | exports.ExampleClient = grpc.makeGenericClientConstructor(ExampleService);
78 |
--------------------------------------------------------------------------------
/example/grpc/build/proto/Example_pb.d.ts:
--------------------------------------------------------------------------------
1 | // package: io.xtech.example
2 | // file: Example.proto
3 |
4 | /* tslint:disable */
5 |
6 | import * as jspb from "google-protobuf";
7 |
8 | export class Movie extends jspb.Message {
9 | getName(): string;
10 | setName(value: string): void;
11 |
12 | getYear(): number;
13 | setYear(value: number): void;
14 |
15 | getRating(): number;
16 | setRating(value: number): void;
17 |
18 | clearCastList(): void;
19 | getCastList(): Array;
20 | setCastList(value: Array): void;
21 | addCast(value: string, index?: number): string;
22 |
23 |
24 | serializeBinary(): Uint8Array;
25 | toObject(includeInstance?: boolean): Movie.AsObject;
26 | static toObject(includeInstance: boolean, msg: Movie): Movie.AsObject;
27 | static extensions: {[key: number]: jspb.ExtensionFieldInfo};
28 | static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo};
29 | static serializeBinaryToWriter(message: Movie, writer: jspb.BinaryWriter): void;
30 | static deserializeBinary(bytes: Uint8Array): Movie;
31 | static deserializeBinaryFromReader(message: Movie, reader: jspb.BinaryReader): Movie;
32 | }
33 |
34 | export namespace Movie {
35 | export type AsObject = {
36 | name: string,
37 | year: number,
38 | rating: number,
39 | castList: Array,
40 | }
41 | }
42 |
43 | export class EmptyRequest extends jspb.Message {
44 |
45 | serializeBinary(): Uint8Array;
46 | toObject(includeInstance?: boolean): EmptyRequest.AsObject;
47 | static toObject(includeInstance: boolean, msg: EmptyRequest): EmptyRequest.AsObject;
48 | static extensions: {[key: number]: jspb.ExtensionFieldInfo};
49 | static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo};
50 | static serializeBinaryToWriter(message: EmptyRequest, writer: jspb.BinaryWriter): void;
51 | static deserializeBinary(bytes: Uint8Array): EmptyRequest;
52 | static deserializeBinaryFromReader(message: EmptyRequest, reader: jspb.BinaryReader): EmptyRequest;
53 | }
54 |
55 | export namespace EmptyRequest {
56 | export type AsObject = {
57 | }
58 | }
59 |
60 | export class SearchByCastInput extends jspb.Message {
61 | getCastname(): string;
62 | setCastname(value: string): void;
63 |
64 |
65 | serializeBinary(): Uint8Array;
66 | toObject(includeInstance?: boolean): SearchByCastInput.AsObject;
67 | static toObject(includeInstance: boolean, msg: SearchByCastInput): SearchByCastInput.AsObject;
68 | static extensions: {[key: number]: jspb.ExtensionFieldInfo};
69 | static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo};
70 | static serializeBinaryToWriter(message: SearchByCastInput, writer: jspb.BinaryWriter): void;
71 | static deserializeBinary(bytes: Uint8Array): SearchByCastInput;
72 | static deserializeBinaryFromReader(message: SearchByCastInput, reader: jspb.BinaryReader): SearchByCastInput;
73 | }
74 |
75 | export namespace SearchByCastInput {
76 | export type AsObject = {
77 | castname: string,
78 | }
79 | }
80 |
81 | export class MoviesResult extends jspb.Message {
82 | clearResultList(): void;
83 | getResultList(): Array;
84 | setResultList(value: Array): void;
85 | addResult(value?: Movie, index?: number): Movie;
86 |
87 |
88 | serializeBinary(): Uint8Array;
89 | toObject(includeInstance?: boolean): MoviesResult.AsObject;
90 | static toObject(includeInstance: boolean, msg: MoviesResult): MoviesResult.AsObject;
91 | static extensions: {[key: number]: jspb.ExtensionFieldInfo};
92 | static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo};
93 | static serializeBinaryToWriter(message: MoviesResult, writer: jspb.BinaryWriter): void;
94 | static deserializeBinary(bytes: Uint8Array): MoviesResult;
95 | static deserializeBinaryFromReader(message: MoviesResult, reader: jspb.BinaryReader): MoviesResult;
96 | }
97 |
98 | export namespace MoviesResult {
99 | export type AsObject = {
100 | resultList: Array,
101 | }
102 | }
103 |
--------------------------------------------------------------------------------
/example/grpc/build/proto/Example_pb.js:
--------------------------------------------------------------------------------
1 | /**
2 | * @fileoverview
3 | * @enhanceable
4 | * @suppress {messageConventions} JS Compiler reports an error if a variable or
5 | * field starts with 'MSG_' and isn't a translatable message.
6 | * @public
7 | */
8 | // GENERATED CODE -- DO NOT EDIT!
9 |
10 | var jspb = require('google-protobuf');
11 | var goog = jspb;
12 | var global = Function('return this')();
13 |
14 | goog.exportSymbol('proto.io.xtech.example.EmptyRequest', null, global);
15 | goog.exportSymbol('proto.io.xtech.example.Movie', null, global);
16 | goog.exportSymbol('proto.io.xtech.example.MoviesResult', null, global);
17 | goog.exportSymbol('proto.io.xtech.example.SearchByCastInput', null, global);
18 |
19 | /**
20 | * Generated by JsPbCodeGenerator.
21 | * @param {Array=} opt_data Optional initial data array, typically from a
22 | * server response, or constructed directly in Javascript. The array is used
23 | * in place and becomes part of the constructed object. It is not cloned.
24 | * If no data is provided, the constructed object will be empty, but still
25 | * valid.
26 | * @extends {jspb.Message}
27 | * @constructor
28 | */
29 | proto.io.xtech.example.Movie = function(opt_data) {
30 | jspb.Message.initialize(this, opt_data, 0, -1, proto.io.xtech.example.Movie.repeatedFields_, null);
31 | };
32 | goog.inherits(proto.io.xtech.example.Movie, jspb.Message);
33 | if (goog.DEBUG && !COMPILED) {
34 | proto.io.xtech.example.Movie.displayName = 'proto.io.xtech.example.Movie';
35 | }
36 | /**
37 | * List of repeated fields within this message type.
38 | * @private {!Array}
39 | * @const
40 | */
41 | proto.io.xtech.example.Movie.repeatedFields_ = [4];
42 |
43 |
44 |
45 | if (jspb.Message.GENERATE_TO_OBJECT) {
46 | /**
47 | * Creates an object representation of this proto suitable for use in Soy templates.
48 | * Field names that are reserved in JavaScript and will be renamed to pb_name.
49 | * To access a reserved field use, foo.pb_, eg, foo.pb_default.
50 | * For the list of reserved names please see:
51 | * com.google.apps.jspb.JsClassTemplate.JS_RESERVED_WORDS.
52 | * @param {boolean=} opt_includeInstance Whether to include the JSPB instance
53 | * for transitional soy proto support: http://goto/soy-param-migration
54 | * @return {!Object}
55 | */
56 | proto.io.xtech.example.Movie.prototype.toObject = function(opt_includeInstance) {
57 | return proto.io.xtech.example.Movie.toObject(opt_includeInstance, this);
58 | };
59 |
60 |
61 | /**
62 | * Static version of the {@see toObject} method.
63 | * @param {boolean|undefined} includeInstance Whether to include the JSPB
64 | * instance for transitional soy proto support:
65 | * http://goto/soy-param-migration
66 | * @param {!proto.io.xtech.example.Movie} msg The msg instance to transform.
67 | * @return {!Object}
68 | * @suppress {unusedLocalVariables} f is only used for nested messages
69 | */
70 | proto.io.xtech.example.Movie.toObject = function(includeInstance, msg) {
71 | var f, obj = {
72 | name: jspb.Message.getFieldWithDefault(msg, 1, ""),
73 | year: jspb.Message.getFieldWithDefault(msg, 2, 0),
74 | rating: +jspb.Message.getFieldWithDefault(msg, 3, 0.0),
75 | castList: jspb.Message.getRepeatedField(msg, 4)
76 | };
77 |
78 | if (includeInstance) {
79 | obj.$jspbMessageInstance = msg;
80 | }
81 | return obj;
82 | };
83 | }
84 |
85 |
86 | /**
87 | * Deserializes binary data (in protobuf wire format).
88 | * @param {jspb.ByteSource} bytes The bytes to deserialize.
89 | * @return {!proto.io.xtech.example.Movie}
90 | */
91 | proto.io.xtech.example.Movie.deserializeBinary = function(bytes) {
92 | var reader = new jspb.BinaryReader(bytes);
93 | var msg = new proto.io.xtech.example.Movie;
94 | return proto.io.xtech.example.Movie.deserializeBinaryFromReader(msg, reader);
95 | };
96 |
97 |
98 | /**
99 | * Deserializes binary data (in protobuf wire format) from the
100 | * given reader into the given message object.
101 | * @param {!proto.io.xtech.example.Movie} msg The message object to deserialize into.
102 | * @param {!jspb.BinaryReader} reader The BinaryReader to use.
103 | * @return {!proto.io.xtech.example.Movie}
104 | */
105 | proto.io.xtech.example.Movie.deserializeBinaryFromReader = function(msg, reader) {
106 | while (reader.nextField()) {
107 | if (reader.isEndGroup()) {
108 | break;
109 | }
110 | var field = reader.getFieldNumber();
111 | switch (field) {
112 | case 1:
113 | var value = /** @type {string} */ (reader.readString());
114 | msg.setName(value);
115 | break;
116 | case 2:
117 | var value = /** @type {number} */ (reader.readInt32());
118 | msg.setYear(value);
119 | break;
120 | case 3:
121 | var value = /** @type {number} */ (reader.readFloat());
122 | msg.setRating(value);
123 | break;
124 | case 4:
125 | var value = /** @type {string} */ (reader.readString());
126 | msg.addCast(value);
127 | break;
128 | default:
129 | reader.skipField();
130 | break;
131 | }
132 | }
133 | return msg;
134 | };
135 |
136 |
137 | /**
138 | * Serializes the message to binary data (in protobuf wire format).
139 | * @return {!Uint8Array}
140 | */
141 | proto.io.xtech.example.Movie.prototype.serializeBinary = function() {
142 | var writer = new jspb.BinaryWriter();
143 | proto.io.xtech.example.Movie.serializeBinaryToWriter(this, writer);
144 | return writer.getResultBuffer();
145 | };
146 |
147 |
148 | /**
149 | * Serializes the given message to binary data (in protobuf wire
150 | * format), writing to the given BinaryWriter.
151 | * @param {!proto.io.xtech.example.Movie} message
152 | * @param {!jspb.BinaryWriter} writer
153 | * @suppress {unusedLocalVariables} f is only used for nested messages
154 | */
155 | proto.io.xtech.example.Movie.serializeBinaryToWriter = function(message, writer) {
156 | var f = undefined;
157 | f = message.getName();
158 | if (f.length > 0) {
159 | writer.writeString(
160 | 1,
161 | f
162 | );
163 | }
164 | f = message.getYear();
165 | if (f !== 0) {
166 | writer.writeInt32(
167 | 2,
168 | f
169 | );
170 | }
171 | f = message.getRating();
172 | if (f !== 0.0) {
173 | writer.writeFloat(
174 | 3,
175 | f
176 | );
177 | }
178 | f = message.getCastList();
179 | if (f.length > 0) {
180 | writer.writeRepeatedString(
181 | 4,
182 | f
183 | );
184 | }
185 | };
186 |
187 |
188 | /**
189 | * optional string name = 1;
190 | * @return {string}
191 | */
192 | proto.io.xtech.example.Movie.prototype.getName = function() {
193 | return /** @type {string} */ (jspb.Message.getFieldWithDefault(this, 1, ""));
194 | };
195 |
196 |
197 | /** @param {string} value */
198 | proto.io.xtech.example.Movie.prototype.setName = function(value) {
199 | jspb.Message.setField(this, 1, value);
200 | };
201 |
202 |
203 | /**
204 | * optional int32 year = 2;
205 | * @return {number}
206 | */
207 | proto.io.xtech.example.Movie.prototype.getYear = function() {
208 | return /** @type {number} */ (jspb.Message.getFieldWithDefault(this, 2, 0));
209 | };
210 |
211 |
212 | /** @param {number} value */
213 | proto.io.xtech.example.Movie.prototype.setYear = function(value) {
214 | jspb.Message.setField(this, 2, value);
215 | };
216 |
217 |
218 | /**
219 | * optional float rating = 3;
220 | * @return {number}
221 | */
222 | proto.io.xtech.example.Movie.prototype.getRating = function() {
223 | return /** @type {number} */ (+jspb.Message.getFieldWithDefault(this, 3, 0.0));
224 | };
225 |
226 |
227 | /** @param {number} value */
228 | proto.io.xtech.example.Movie.prototype.setRating = function(value) {
229 | jspb.Message.setField(this, 3, value);
230 | };
231 |
232 |
233 | /**
234 | * repeated string cast = 4;
235 | * @return {!Array.}
236 | */
237 | proto.io.xtech.example.Movie.prototype.getCastList = function() {
238 | return /** @type {!Array.} */ (jspb.Message.getRepeatedField(this, 4));
239 | };
240 |
241 |
242 | /** @param {!Array.} value */
243 | proto.io.xtech.example.Movie.prototype.setCastList = function(value) {
244 | jspb.Message.setField(this, 4, value || []);
245 | };
246 |
247 |
248 | /**
249 | * @param {!string} value
250 | * @param {number=} opt_index
251 | */
252 | proto.io.xtech.example.Movie.prototype.addCast = function(value, opt_index) {
253 | jspb.Message.addToRepeatedField(this, 4, value, opt_index);
254 | };
255 |
256 |
257 | proto.io.xtech.example.Movie.prototype.clearCastList = function() {
258 | this.setCastList([]);
259 | };
260 |
261 |
262 |
263 | /**
264 | * Generated by JsPbCodeGenerator.
265 | * @param {Array=} opt_data Optional initial data array, typically from a
266 | * server response, or constructed directly in Javascript. The array is used
267 | * in place and becomes part of the constructed object. It is not cloned.
268 | * If no data is provided, the constructed object will be empty, but still
269 | * valid.
270 | * @extends {jspb.Message}
271 | * @constructor
272 | */
273 | proto.io.xtech.example.EmptyRequest = function(opt_data) {
274 | jspb.Message.initialize(this, opt_data, 0, -1, null, null);
275 | };
276 | goog.inherits(proto.io.xtech.example.EmptyRequest, jspb.Message);
277 | if (goog.DEBUG && !COMPILED) {
278 | proto.io.xtech.example.EmptyRequest.displayName = 'proto.io.xtech.example.EmptyRequest';
279 | }
280 |
281 |
282 | if (jspb.Message.GENERATE_TO_OBJECT) {
283 | /**
284 | * Creates an object representation of this proto suitable for use in Soy templates.
285 | * Field names that are reserved in JavaScript and will be renamed to pb_name.
286 | * To access a reserved field use, foo.pb_, eg, foo.pb_default.
287 | * For the list of reserved names please see:
288 | * com.google.apps.jspb.JsClassTemplate.JS_RESERVED_WORDS.
289 | * @param {boolean=} opt_includeInstance Whether to include the JSPB instance
290 | * for transitional soy proto support: http://goto/soy-param-migration
291 | * @return {!Object}
292 | */
293 | proto.io.xtech.example.EmptyRequest.prototype.toObject = function(opt_includeInstance) {
294 | return proto.io.xtech.example.EmptyRequest.toObject(opt_includeInstance, this);
295 | };
296 |
297 |
298 | /**
299 | * Static version of the {@see toObject} method.
300 | * @param {boolean|undefined} includeInstance Whether to include the JSPB
301 | * instance for transitional soy proto support:
302 | * http://goto/soy-param-migration
303 | * @param {!proto.io.xtech.example.EmptyRequest} msg The msg instance to transform.
304 | * @return {!Object}
305 | * @suppress {unusedLocalVariables} f is only used for nested messages
306 | */
307 | proto.io.xtech.example.EmptyRequest.toObject = function(includeInstance, msg) {
308 | var f, obj = {
309 |
310 | };
311 |
312 | if (includeInstance) {
313 | obj.$jspbMessageInstance = msg;
314 | }
315 | return obj;
316 | };
317 | }
318 |
319 |
320 | /**
321 | * Deserializes binary data (in protobuf wire format).
322 | * @param {jspb.ByteSource} bytes The bytes to deserialize.
323 | * @return {!proto.io.xtech.example.EmptyRequest}
324 | */
325 | proto.io.xtech.example.EmptyRequest.deserializeBinary = function(bytes) {
326 | var reader = new jspb.BinaryReader(bytes);
327 | var msg = new proto.io.xtech.example.EmptyRequest;
328 | return proto.io.xtech.example.EmptyRequest.deserializeBinaryFromReader(msg, reader);
329 | };
330 |
331 |
332 | /**
333 | * Deserializes binary data (in protobuf wire format) from the
334 | * given reader into the given message object.
335 | * @param {!proto.io.xtech.example.EmptyRequest} msg The message object to deserialize into.
336 | * @param {!jspb.BinaryReader} reader The BinaryReader to use.
337 | * @return {!proto.io.xtech.example.EmptyRequest}
338 | */
339 | proto.io.xtech.example.EmptyRequest.deserializeBinaryFromReader = function(msg, reader) {
340 | while (reader.nextField()) {
341 | if (reader.isEndGroup()) {
342 | break;
343 | }
344 | var field = reader.getFieldNumber();
345 | switch (field) {
346 | default:
347 | reader.skipField();
348 | break;
349 | }
350 | }
351 | return msg;
352 | };
353 |
354 |
355 | /**
356 | * Serializes the message to binary data (in protobuf wire format).
357 | * @return {!Uint8Array}
358 | */
359 | proto.io.xtech.example.EmptyRequest.prototype.serializeBinary = function() {
360 | var writer = new jspb.BinaryWriter();
361 | proto.io.xtech.example.EmptyRequest.serializeBinaryToWriter(this, writer);
362 | return writer.getResultBuffer();
363 | };
364 |
365 |
366 | /**
367 | * Serializes the given message to binary data (in protobuf wire
368 | * format), writing to the given BinaryWriter.
369 | * @param {!proto.io.xtech.example.EmptyRequest} message
370 | * @param {!jspb.BinaryWriter} writer
371 | * @suppress {unusedLocalVariables} f is only used for nested messages
372 | */
373 | proto.io.xtech.example.EmptyRequest.serializeBinaryToWriter = function(message, writer) {
374 | var f = undefined;
375 | };
376 |
377 |
378 |
379 | /**
380 | * Generated by JsPbCodeGenerator.
381 | * @param {Array=} opt_data Optional initial data array, typically from a
382 | * server response, or constructed directly in Javascript. The array is used
383 | * in place and becomes part of the constructed object. It is not cloned.
384 | * If no data is provided, the constructed object will be empty, but still
385 | * valid.
386 | * @extends {jspb.Message}
387 | * @constructor
388 | */
389 | proto.io.xtech.example.SearchByCastInput = function(opt_data) {
390 | jspb.Message.initialize(this, opt_data, 0, -1, null, null);
391 | };
392 | goog.inherits(proto.io.xtech.example.SearchByCastInput, jspb.Message);
393 | if (goog.DEBUG && !COMPILED) {
394 | proto.io.xtech.example.SearchByCastInput.displayName = 'proto.io.xtech.example.SearchByCastInput';
395 | }
396 |
397 |
398 | if (jspb.Message.GENERATE_TO_OBJECT) {
399 | /**
400 | * Creates an object representation of this proto suitable for use in Soy templates.
401 | * Field names that are reserved in JavaScript and will be renamed to pb_name.
402 | * To access a reserved field use, foo.pb_, eg, foo.pb_default.
403 | * For the list of reserved names please see:
404 | * com.google.apps.jspb.JsClassTemplate.JS_RESERVED_WORDS.
405 | * @param {boolean=} opt_includeInstance Whether to include the JSPB instance
406 | * for transitional soy proto support: http://goto/soy-param-migration
407 | * @return {!Object}
408 | */
409 | proto.io.xtech.example.SearchByCastInput.prototype.toObject = function(opt_includeInstance) {
410 | return proto.io.xtech.example.SearchByCastInput.toObject(opt_includeInstance, this);
411 | };
412 |
413 |
414 | /**
415 | * Static version of the {@see toObject} method.
416 | * @param {boolean|undefined} includeInstance Whether to include the JSPB
417 | * instance for transitional soy proto support:
418 | * http://goto/soy-param-migration
419 | * @param {!proto.io.xtech.example.SearchByCastInput} msg The msg instance to transform.
420 | * @return {!Object}
421 | * @suppress {unusedLocalVariables} f is only used for nested messages
422 | */
423 | proto.io.xtech.example.SearchByCastInput.toObject = function(includeInstance, msg) {
424 | var f, obj = {
425 | castname: jspb.Message.getFieldWithDefault(msg, 1, "")
426 | };
427 |
428 | if (includeInstance) {
429 | obj.$jspbMessageInstance = msg;
430 | }
431 | return obj;
432 | };
433 | }
434 |
435 |
436 | /**
437 | * Deserializes binary data (in protobuf wire format).
438 | * @param {jspb.ByteSource} bytes The bytes to deserialize.
439 | * @return {!proto.io.xtech.example.SearchByCastInput}
440 | */
441 | proto.io.xtech.example.SearchByCastInput.deserializeBinary = function(bytes) {
442 | var reader = new jspb.BinaryReader(bytes);
443 | var msg = new proto.io.xtech.example.SearchByCastInput;
444 | return proto.io.xtech.example.SearchByCastInput.deserializeBinaryFromReader(msg, reader);
445 | };
446 |
447 |
448 | /**
449 | * Deserializes binary data (in protobuf wire format) from the
450 | * given reader into the given message object.
451 | * @param {!proto.io.xtech.example.SearchByCastInput} msg The message object to deserialize into.
452 | * @param {!jspb.BinaryReader} reader The BinaryReader to use.
453 | * @return {!proto.io.xtech.example.SearchByCastInput}
454 | */
455 | proto.io.xtech.example.SearchByCastInput.deserializeBinaryFromReader = function(msg, reader) {
456 | while (reader.nextField()) {
457 | if (reader.isEndGroup()) {
458 | break;
459 | }
460 | var field = reader.getFieldNumber();
461 | switch (field) {
462 | case 1:
463 | var value = /** @type {string} */ (reader.readString());
464 | msg.setCastname(value);
465 | break;
466 | default:
467 | reader.skipField();
468 | break;
469 | }
470 | }
471 | return msg;
472 | };
473 |
474 |
475 | /**
476 | * Serializes the message to binary data (in protobuf wire format).
477 | * @return {!Uint8Array}
478 | */
479 | proto.io.xtech.example.SearchByCastInput.prototype.serializeBinary = function() {
480 | var writer = new jspb.BinaryWriter();
481 | proto.io.xtech.example.SearchByCastInput.serializeBinaryToWriter(this, writer);
482 | return writer.getResultBuffer();
483 | };
484 |
485 |
486 | /**
487 | * Serializes the given message to binary data (in protobuf wire
488 | * format), writing to the given BinaryWriter.
489 | * @param {!proto.io.xtech.example.SearchByCastInput} message
490 | * @param {!jspb.BinaryWriter} writer
491 | * @suppress {unusedLocalVariables} f is only used for nested messages
492 | */
493 | proto.io.xtech.example.SearchByCastInput.serializeBinaryToWriter = function(message, writer) {
494 | var f = undefined;
495 | f = message.getCastname();
496 | if (f.length > 0) {
497 | writer.writeString(
498 | 1,
499 | f
500 | );
501 | }
502 | };
503 |
504 |
505 | /**
506 | * optional string castName = 1;
507 | * @return {string}
508 | */
509 | proto.io.xtech.example.SearchByCastInput.prototype.getCastname = function() {
510 | return /** @type {string} */ (jspb.Message.getFieldWithDefault(this, 1, ""));
511 | };
512 |
513 |
514 | /** @param {string} value */
515 | proto.io.xtech.example.SearchByCastInput.prototype.setCastname = function(value) {
516 | jspb.Message.setField(this, 1, value);
517 | };
518 |
519 |
520 |
521 | /**
522 | * Generated by JsPbCodeGenerator.
523 | * @param {Array=} opt_data Optional initial data array, typically from a
524 | * server response, or constructed directly in Javascript. The array is used
525 | * in place and becomes part of the constructed object. It is not cloned.
526 | * If no data is provided, the constructed object will be empty, but still
527 | * valid.
528 | * @extends {jspb.Message}
529 | * @constructor
530 | */
531 | proto.io.xtech.example.MoviesResult = function(opt_data) {
532 | jspb.Message.initialize(this, opt_data, 0, -1, proto.io.xtech.example.MoviesResult.repeatedFields_, null);
533 | };
534 | goog.inherits(proto.io.xtech.example.MoviesResult, jspb.Message);
535 | if (goog.DEBUG && !COMPILED) {
536 | proto.io.xtech.example.MoviesResult.displayName = 'proto.io.xtech.example.MoviesResult';
537 | }
538 | /**
539 | * List of repeated fields within this message type.
540 | * @private {!Array}
541 | * @const
542 | */
543 | proto.io.xtech.example.MoviesResult.repeatedFields_ = [1];
544 |
545 |
546 |
547 | if (jspb.Message.GENERATE_TO_OBJECT) {
548 | /**
549 | * Creates an object representation of this proto suitable for use in Soy templates.
550 | * Field names that are reserved in JavaScript and will be renamed to pb_name.
551 | * To access a reserved field use, foo.pb_, eg, foo.pb_default.
552 | * For the list of reserved names please see:
553 | * com.google.apps.jspb.JsClassTemplate.JS_RESERVED_WORDS.
554 | * @param {boolean=} opt_includeInstance Whether to include the JSPB instance
555 | * for transitional soy proto support: http://goto/soy-param-migration
556 | * @return {!Object}
557 | */
558 | proto.io.xtech.example.MoviesResult.prototype.toObject = function(opt_includeInstance) {
559 | return proto.io.xtech.example.MoviesResult.toObject(opt_includeInstance, this);
560 | };
561 |
562 |
563 | /**
564 | * Static version of the {@see toObject} method.
565 | * @param {boolean|undefined} includeInstance Whether to include the JSPB
566 | * instance for transitional soy proto support:
567 | * http://goto/soy-param-migration
568 | * @param {!proto.io.xtech.example.MoviesResult} msg The msg instance to transform.
569 | * @return {!Object}
570 | * @suppress {unusedLocalVariables} f is only used for nested messages
571 | */
572 | proto.io.xtech.example.MoviesResult.toObject = function(includeInstance, msg) {
573 | var f, obj = {
574 | resultList: jspb.Message.toObjectList(msg.getResultList(),
575 | proto.io.xtech.example.Movie.toObject, includeInstance)
576 | };
577 |
578 | if (includeInstance) {
579 | obj.$jspbMessageInstance = msg;
580 | }
581 | return obj;
582 | };
583 | }
584 |
585 |
586 | /**
587 | * Deserializes binary data (in protobuf wire format).
588 | * @param {jspb.ByteSource} bytes The bytes to deserialize.
589 | * @return {!proto.io.xtech.example.MoviesResult}
590 | */
591 | proto.io.xtech.example.MoviesResult.deserializeBinary = function(bytes) {
592 | var reader = new jspb.BinaryReader(bytes);
593 | var msg = new proto.io.xtech.example.MoviesResult;
594 | return proto.io.xtech.example.MoviesResult.deserializeBinaryFromReader(msg, reader);
595 | };
596 |
597 |
598 | /**
599 | * Deserializes binary data (in protobuf wire format) from the
600 | * given reader into the given message object.
601 | * @param {!proto.io.xtech.example.MoviesResult} msg The message object to deserialize into.
602 | * @param {!jspb.BinaryReader} reader The BinaryReader to use.
603 | * @return {!proto.io.xtech.example.MoviesResult}
604 | */
605 | proto.io.xtech.example.MoviesResult.deserializeBinaryFromReader = function(msg, reader) {
606 | while (reader.nextField()) {
607 | if (reader.isEndGroup()) {
608 | break;
609 | }
610 | var field = reader.getFieldNumber();
611 | switch (field) {
612 | case 1:
613 | var value = new proto.io.xtech.example.Movie;
614 | reader.readMessage(value,proto.io.xtech.example.Movie.deserializeBinaryFromReader);
615 | msg.addResult(value);
616 | break;
617 | default:
618 | reader.skipField();
619 | break;
620 | }
621 | }
622 | return msg;
623 | };
624 |
625 |
626 | /**
627 | * Serializes the message to binary data (in protobuf wire format).
628 | * @return {!Uint8Array}
629 | */
630 | proto.io.xtech.example.MoviesResult.prototype.serializeBinary = function() {
631 | var writer = new jspb.BinaryWriter();
632 | proto.io.xtech.example.MoviesResult.serializeBinaryToWriter(this, writer);
633 | return writer.getResultBuffer();
634 | };
635 |
636 |
637 | /**
638 | * Serializes the given message to binary data (in protobuf wire
639 | * format), writing to the given BinaryWriter.
640 | * @param {!proto.io.xtech.example.MoviesResult} message
641 | * @param {!jspb.BinaryWriter} writer
642 | * @suppress {unusedLocalVariables} f is only used for nested messages
643 | */
644 | proto.io.xtech.example.MoviesResult.serializeBinaryToWriter = function(message, writer) {
645 | var f = undefined;
646 | f = message.getResultList();
647 | if (f.length > 0) {
648 | writer.writeRepeatedMessage(
649 | 1,
650 | f,
651 | proto.io.xtech.example.Movie.serializeBinaryToWriter
652 | );
653 | }
654 | };
655 |
656 |
657 | /**
658 | * repeated Movie result = 1;
659 | * @return {!Array.}
660 | */
661 | proto.io.xtech.example.MoviesResult.prototype.getResultList = function() {
662 | return /** @type{!Array.} */ (
663 | jspb.Message.getRepeatedWrapperField(this, proto.io.xtech.example.Movie, 1));
664 | };
665 |
666 |
667 | /** @param {!Array.} value */
668 | proto.io.xtech.example.MoviesResult.prototype.setResultList = function(value) {
669 | jspb.Message.setRepeatedWrapperField(this, 1, value);
670 | };
671 |
672 |
673 | /**
674 | * @param {!proto.io.xtech.example.Movie=} opt_value
675 | * @param {number=} opt_index
676 | * @return {!proto.io.xtech.example.Movie}
677 | */
678 | proto.io.xtech.example.MoviesResult.prototype.addResult = function(opt_value, opt_index) {
679 | return jspb.Message.addToRepeatedWrapperField(this, 1, opt_value, proto.io.xtech.example.Movie, opt_index);
680 | };
681 |
682 |
683 | proto.io.xtech.example.MoviesResult.prototype.clearResultList = function() {
684 | this.setResultList([]);
685 | };
686 |
687 |
688 | goog.object.extend(exports, proto.io.xtech.example);
689 |
--------------------------------------------------------------------------------
/example/grpc/build/server.d.ts:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env node
2 | export {};
3 |
--------------------------------------------------------------------------------
/example/grpc/build/server.js:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env node
2 | "use strict";
3 | Object.defineProperty(exports, "__esModule", { value: true });
4 | const debug = require("debug");
5 | const grpc = require("grpc");
6 | const Example_grpc_pb_1 = require("./proto/Example_grpc_pb");
7 | const Example_pb_1 = require("./proto/Example_pb");
8 | const log = debug("SampleServer");
9 | const Movies = [
10 | {
11 | cast: ["Tom Cruise", "Simon Pegg", "Jeremy Renner"],
12 | name: "Mission: Impossible Rogue Nation",
13 | rating: 0.97,
14 | year: 2015,
15 | },
16 | {
17 | cast: ["Tom Cruise", "Simon Pegg", "Henry Cavill"],
18 | name: "Mission: Impossible - Fallout",
19 | rating: 0.93,
20 | year: 2018,
21 | },
22 | {
23 | cast: ["Leonardo DiCaprio", "Jonah Hill", "Margot Robbie"],
24 | name: "The Wolf of Wall Street",
25 | rating: 0.78,
26 | year: 2013,
27 | },
28 | ];
29 | function createMovie(movie) {
30 | const result = new Example_pb_1.Movie();
31 | result.setCastList(movie.cast);
32 | result.setName(movie.name);
33 | result.setYear(movie.year);
34 | result.setRating(movie.rating);
35 | return result;
36 | }
37 | class ServerImpl {
38 | setMovies(request, callback) {
39 | const result = new Example_pb_1.MoviesResult();
40 | Movies.map(createMovie).forEach((movie) => result.addResult(movie));
41 | callback(null, result);
42 | }
43 | searchMoviesByCast(call) {
44 | log("call started");
45 | const input = call.request;
46 | let i = 1;
47 | call.on("error", (error) => {
48 | log(error);
49 | call.end();
50 | });
51 | Movies.map(createMovie).forEach((movie) => {
52 | if (movie.getCastList().indexOf(input.getCastname()) > -1) {
53 | setTimeout(() => {
54 | log(movie.getName());
55 | call.write(movie);
56 | }, i * 1000);
57 | i += 1;
58 | }
59 | });
60 | setTimeout(() => {
61 | call.end();
62 | log("call ended");
63 | }, 3000);
64 | }
65 | }
66 | function startServer() {
67 | const server = new grpc.Server();
68 | server.addService(Example_grpc_pb_1.ExampleService, new ServerImpl());
69 | server.bind("0.0.0.0:50051", grpc.ServerCredentials.createInsecure());
70 | server.start();
71 | log("Server started, listening: 0.0.0.0:50051");
72 | }
73 | startServer();
74 | process.on("uncaughtException", (err) => {
75 | log(`process on uncaughtException error: ${err}`);
76 | });
77 | process.on("unhandledRejection", (err) => {
78 | log(`process on unhandledRejection error: ${err}`);
79 | });
80 | //# sourceMappingURL=server.js.map
--------------------------------------------------------------------------------
/example/grpc/build/server.js.map:
--------------------------------------------------------------------------------
1 | {"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"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"}
--------------------------------------------------------------------------------
/example/grpc/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "grpc-graphql-schema-example-grpc",
3 | "version": "1.0.0",
4 | "description": "",
5 | "main": "index.js",
6 | "directories": {
7 | "example": "example"
8 | },
9 | "scripts": {
10 | "postinstall": "npm run build",
11 | "build": "bash bash/build.sh",
12 | "start": "bash bash/server.sh",
13 | "test": "echo \"Error: no test specified\" && exit 1"
14 | },
15 | "author": "",
16 | "license": "ISC",
17 | "dependencies": {
18 | "debug": "^4.1.1",
19 | "google-protobuf": "^3.6.1",
20 | "grpc": "^1.17.0"
21 | },
22 | "devDependencies": {
23 | "@types/debug": "^0.0.31",
24 | "@types/google-protobuf": "^3.2.7",
25 | "@types/node": "^10.12.18",
26 | "grpc-tools": "^1.6.6",
27 | "grpc_tools_node_protoc_ts": "^2.4.2",
28 | "typescript": "^3.2.2"
29 | }
30 | }
31 |
--------------------------------------------------------------------------------
/example/grpc/proto/Example.proto:
--------------------------------------------------------------------------------
1 | syntax = "proto3";
2 |
3 | package io.xtech.example;
4 |
5 | /**
6 | * movie message payload
7 | */
8 | message Movie {
9 | string name = 1;
10 | int32 year = 2;
11 | float rating = 3;
12 |
13 | /**
14 | * list of cast
15 | */
16 | repeated string cast = 4;
17 | }
18 |
19 | message EmptyRequest {}
20 |
21 | message SearchByCastInput {
22 | string castName = 1;
23 | }
24 |
25 | /**
26 | * movie result message, contains list of movies
27 | */
28 | message MoviesResult {
29 | /**
30 | * list of movies
31 | */
32 | repeated Movie result = 1;
33 | }
34 |
35 | service Example {
36 | /**
37 | * get all movies
38 | */
39 | rpc GetMovies (EmptyRequest) returns (MoviesResult) {}
40 |
41 | /**
42 | * search movies by the name of the cast
43 | */
44 | rpc SearchMoviesByCast (SearchByCastInput) returns (stream Movie) {}
45 | }
46 |
--------------------------------------------------------------------------------
/example/grpc/src/proto/Example_grpc_pb.d.ts:
--------------------------------------------------------------------------------
1 | // package: io.xtech.example
2 | // file: Example.proto
3 |
4 | /* tslint:disable */
5 |
6 | import * as grpc from "grpc";
7 | import * as Example_pb from "./Example_pb";
8 |
9 | interface IExampleService extends grpc.ServiceDefinition {
10 | setMovies: IExampleService_ISetMovies;
11 | searchMoviesByCast: IExampleService_ISearchMoviesByCast;
12 | }
13 |
14 | interface IExampleService_ISetMovies extends grpc.MethodDefinition {
15 | path: string; // "/io.xtech.example.Example/SetMovies"
16 | requestStream: boolean; // false
17 | responseStream: boolean; // false
18 | requestSerialize: grpc.serialize;
19 | requestDeserialize: grpc.deserialize;
20 | responseSerialize: grpc.serialize;
21 | responseDeserialize: grpc.deserialize;
22 | }
23 | interface IExampleService_ISearchMoviesByCast extends grpc.MethodDefinition {
24 | path: string; // "/io.xtech.example.Example/SearchMoviesByCast"
25 | requestStream: boolean; // false
26 | responseStream: boolean; // true
27 | requestSerialize: grpc.serialize;
28 | requestDeserialize: grpc.deserialize;
29 | responseSerialize: grpc.serialize;
30 | responseDeserialize: grpc.deserialize;
31 | }
32 |
33 | export const ExampleService: IExampleService;
34 |
35 | export interface IExampleServer {
36 | setMovies: grpc.handleUnaryCall;
37 | searchMoviesByCast: grpc.handleServerStreamingCall;
38 | }
39 |
40 | export interface IExampleClient {
41 | setMovies(request: Example_pb.EmptyRequest, callback: (error: grpc.ServiceError | null, response: Example_pb.MoviesResult) => void): grpc.ClientUnaryCall;
42 | setMovies(request: Example_pb.EmptyRequest, metadata: grpc.Metadata, callback: (error: grpc.ServiceError | null, response: Example_pb.MoviesResult) => void): grpc.ClientUnaryCall;
43 | setMovies(request: Example_pb.EmptyRequest, metadata: grpc.Metadata, options: Partial, callback: (error: grpc.ServiceError | null, response: Example_pb.MoviesResult) => void): grpc.ClientUnaryCall;
44 | searchMoviesByCast(request: Example_pb.SearchByCastInput, options?: Partial): grpc.ClientReadableStream;
45 | searchMoviesByCast(request: Example_pb.SearchByCastInput, metadata?: grpc.Metadata, options?: Partial): grpc.ClientReadableStream;
46 | }
47 |
48 | export class ExampleClient extends grpc.Client implements IExampleClient {
49 | constructor(address: string, credentials: grpc.ChannelCredentials, options?: object);
50 | public setMovies(request: Example_pb.EmptyRequest, callback: (error: grpc.ServiceError | null, response: Example_pb.MoviesResult) => void): grpc.ClientUnaryCall;
51 | public setMovies(request: Example_pb.EmptyRequest, metadata: grpc.Metadata, callback: (error: grpc.ServiceError | null, response: Example_pb.MoviesResult) => void): grpc.ClientUnaryCall;
52 | public setMovies(request: Example_pb.EmptyRequest, metadata: grpc.Metadata, options: Partial, callback: (error: grpc.ServiceError | null, response: Example_pb.MoviesResult) => void): grpc.ClientUnaryCall;
53 | public searchMoviesByCast(request: Example_pb.SearchByCastInput, options?: Partial): grpc.ClientReadableStream;
54 | public searchMoviesByCast(request: Example_pb.SearchByCastInput, metadata?: grpc.Metadata, options?: Partial): grpc.ClientReadableStream;
55 | }
56 |
--------------------------------------------------------------------------------
/example/grpc/src/proto/Example_grpc_pb.js:
--------------------------------------------------------------------------------
1 | // GENERATED CODE -- DO NOT EDIT!
2 |
3 | 'use strict';
4 | var grpc = require('grpc');
5 | var Example_pb = require('./Example_pb.js');
6 |
7 | function serialize_io_xtech_example_EmptyRequest(arg) {
8 | if (!(arg instanceof Example_pb.EmptyRequest)) {
9 | throw new Error('Expected argument of type io.xtech.example.EmptyRequest');
10 | }
11 | return new Buffer(arg.serializeBinary());
12 | }
13 |
14 | function deserialize_io_xtech_example_EmptyRequest(buffer_arg) {
15 | return Example_pb.EmptyRequest.deserializeBinary(new Uint8Array(buffer_arg));
16 | }
17 |
18 | function serialize_io_xtech_example_Movie(arg) {
19 | if (!(arg instanceof Example_pb.Movie)) {
20 | throw new Error('Expected argument of type io.xtech.example.Movie');
21 | }
22 | return new Buffer(arg.serializeBinary());
23 | }
24 |
25 | function deserialize_io_xtech_example_Movie(buffer_arg) {
26 | return Example_pb.Movie.deserializeBinary(new Uint8Array(buffer_arg));
27 | }
28 |
29 | function serialize_io_xtech_example_MoviesResult(arg) {
30 | if (!(arg instanceof Example_pb.MoviesResult)) {
31 | throw new Error('Expected argument of type io.xtech.example.MoviesResult');
32 | }
33 | return new Buffer(arg.serializeBinary());
34 | }
35 |
36 | function deserialize_io_xtech_example_MoviesResult(buffer_arg) {
37 | return Example_pb.MoviesResult.deserializeBinary(new Uint8Array(buffer_arg));
38 | }
39 |
40 | function serialize_io_xtech_example_SearchByCastInput(arg) {
41 | if (!(arg instanceof Example_pb.SearchByCastInput)) {
42 | throw new Error('Expected argument of type io.xtech.example.SearchByCastInput');
43 | }
44 | return new Buffer(arg.serializeBinary());
45 | }
46 |
47 | function deserialize_io_xtech_example_SearchByCastInput(buffer_arg) {
48 | return Example_pb.SearchByCastInput.deserializeBinary(new Uint8Array(buffer_arg));
49 | }
50 |
51 |
52 | var ExampleService = exports.ExampleService = {
53 | setMovies: {
54 | path: '/io.xtech.example.Example/SetMovies',
55 | requestStream: false,
56 | responseStream: false,
57 | requestType: Example_pb.EmptyRequest,
58 | responseType: Example_pb.MoviesResult,
59 | requestSerialize: serialize_io_xtech_example_EmptyRequest,
60 | requestDeserialize: deserialize_io_xtech_example_EmptyRequest,
61 | responseSerialize: serialize_io_xtech_example_MoviesResult,
62 | responseDeserialize: deserialize_io_xtech_example_MoviesResult,
63 | },
64 | searchMoviesByCast: {
65 | path: '/io.xtech.example.Example/SearchMoviesByCast',
66 | requestStream: false,
67 | responseStream: true,
68 | requestType: Example_pb.SearchByCastInput,
69 | responseType: Example_pb.Movie,
70 | requestSerialize: serialize_io_xtech_example_SearchByCastInput,
71 | requestDeserialize: deserialize_io_xtech_example_SearchByCastInput,
72 | responseSerialize: serialize_io_xtech_example_Movie,
73 | responseDeserialize: deserialize_io_xtech_example_Movie,
74 | },
75 | };
76 |
77 | exports.ExampleClient = grpc.makeGenericClientConstructor(ExampleService);
78 |
--------------------------------------------------------------------------------
/example/grpc/src/proto/Example_pb.d.ts:
--------------------------------------------------------------------------------
1 | // package: io.xtech.example
2 | // file: Example.proto
3 |
4 | /* tslint:disable */
5 |
6 | import * as jspb from "google-protobuf";
7 |
8 | export class Movie extends jspb.Message {
9 | getName(): string;
10 | setName(value: string): void;
11 |
12 | getYear(): number;
13 | setYear(value: number): void;
14 |
15 | getRating(): number;
16 | setRating(value: number): void;
17 |
18 | clearCastList(): void;
19 | getCastList(): Array;
20 | setCastList(value: Array): void;
21 | addCast(value: string, index?: number): string;
22 |
23 |
24 | serializeBinary(): Uint8Array;
25 | toObject(includeInstance?: boolean): Movie.AsObject;
26 | static toObject(includeInstance: boolean, msg: Movie): Movie.AsObject;
27 | static extensions: {[key: number]: jspb.ExtensionFieldInfo};
28 | static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo};
29 | static serializeBinaryToWriter(message: Movie, writer: jspb.BinaryWriter): void;
30 | static deserializeBinary(bytes: Uint8Array): Movie;
31 | static deserializeBinaryFromReader(message: Movie, reader: jspb.BinaryReader): Movie;
32 | }
33 |
34 | export namespace Movie {
35 | export type AsObject = {
36 | name: string,
37 | year: number,
38 | rating: number,
39 | castList: Array,
40 | }
41 | }
42 |
43 | export class EmptyRequest extends jspb.Message {
44 |
45 | serializeBinary(): Uint8Array;
46 | toObject(includeInstance?: boolean): EmptyRequest.AsObject;
47 | static toObject(includeInstance: boolean, msg: EmptyRequest): EmptyRequest.AsObject;
48 | static extensions: {[key: number]: jspb.ExtensionFieldInfo};
49 | static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo};
50 | static serializeBinaryToWriter(message: EmptyRequest, writer: jspb.BinaryWriter): void;
51 | static deserializeBinary(bytes: Uint8Array): EmptyRequest;
52 | static deserializeBinaryFromReader(message: EmptyRequest, reader: jspb.BinaryReader): EmptyRequest;
53 | }
54 |
55 | export namespace EmptyRequest {
56 | export type AsObject = {
57 | }
58 | }
59 |
60 | export class SearchByCastInput extends jspb.Message {
61 | getCastname(): string;
62 | setCastname(value: string): void;
63 |
64 |
65 | serializeBinary(): Uint8Array;
66 | toObject(includeInstance?: boolean): SearchByCastInput.AsObject;
67 | static toObject(includeInstance: boolean, msg: SearchByCastInput): SearchByCastInput.AsObject;
68 | static extensions: {[key: number]: jspb.ExtensionFieldInfo};
69 | static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo};
70 | static serializeBinaryToWriter(message: SearchByCastInput, writer: jspb.BinaryWriter): void;
71 | static deserializeBinary(bytes: Uint8Array): SearchByCastInput;
72 | static deserializeBinaryFromReader(message: SearchByCastInput, reader: jspb.BinaryReader): SearchByCastInput;
73 | }
74 |
75 | export namespace SearchByCastInput {
76 | export type AsObject = {
77 | castname: string,
78 | }
79 | }
80 |
81 | export class MoviesResult extends jspb.Message {
82 | clearResultList(): void;
83 | getResultList(): Array;
84 | setResultList(value: Array): void;
85 | addResult(value?: Movie, index?: number): Movie;
86 |
87 |
88 | serializeBinary(): Uint8Array;
89 | toObject(includeInstance?: boolean): MoviesResult.AsObject;
90 | static toObject(includeInstance: boolean, msg: MoviesResult): MoviesResult.AsObject;
91 | static extensions: {[key: number]: jspb.ExtensionFieldInfo};
92 | static extensionsBinary: {[key: number]: jspb.ExtensionFieldBinaryInfo};
93 | static serializeBinaryToWriter(message: MoviesResult, writer: jspb.BinaryWriter): void;
94 | static deserializeBinary(bytes: Uint8Array): MoviesResult;
95 | static deserializeBinaryFromReader(message: MoviesResult, reader: jspb.BinaryReader): MoviesResult;
96 | }
97 |
98 | export namespace MoviesResult {
99 | export type AsObject = {
100 | resultList: Array,
101 | }
102 | }
103 |
--------------------------------------------------------------------------------
/example/grpc/src/proto/Example_pb.js:
--------------------------------------------------------------------------------
1 | /**
2 | * @fileoverview
3 | * @enhanceable
4 | * @suppress {messageConventions} JS Compiler reports an error if a variable or
5 | * field starts with 'MSG_' and isn't a translatable message.
6 | * @public
7 | */
8 | // GENERATED CODE -- DO NOT EDIT!
9 |
10 | var jspb = require('google-protobuf');
11 | var goog = jspb;
12 | var global = Function('return this')();
13 |
14 | goog.exportSymbol('proto.io.xtech.example.EmptyRequest', null, global);
15 | goog.exportSymbol('proto.io.xtech.example.Movie', null, global);
16 | goog.exportSymbol('proto.io.xtech.example.MoviesResult', null, global);
17 | goog.exportSymbol('proto.io.xtech.example.SearchByCastInput', null, global);
18 |
19 | /**
20 | * Generated by JsPbCodeGenerator.
21 | * @param {Array=} opt_data Optional initial data array, typically from a
22 | * server response, or constructed directly in Javascript. The array is used
23 | * in place and becomes part of the constructed object. It is not cloned.
24 | * If no data is provided, the constructed object will be empty, but still
25 | * valid.
26 | * @extends {jspb.Message}
27 | * @constructor
28 | */
29 | proto.io.xtech.example.Movie = function(opt_data) {
30 | jspb.Message.initialize(this, opt_data, 0, -1, proto.io.xtech.example.Movie.repeatedFields_, null);
31 | };
32 | goog.inherits(proto.io.xtech.example.Movie, jspb.Message);
33 | if (goog.DEBUG && !COMPILED) {
34 | proto.io.xtech.example.Movie.displayName = 'proto.io.xtech.example.Movie';
35 | }
36 | /**
37 | * List of repeated fields within this message type.
38 | * @private {!Array}
39 | * @const
40 | */
41 | proto.io.xtech.example.Movie.repeatedFields_ = [4];
42 |
43 |
44 |
45 | if (jspb.Message.GENERATE_TO_OBJECT) {
46 | /**
47 | * Creates an object representation of this proto suitable for use in Soy templates.
48 | * Field names that are reserved in JavaScript and will be renamed to pb_name.
49 | * To access a reserved field use, foo.pb_, eg, foo.pb_default.
50 | * For the list of reserved names please see:
51 | * com.google.apps.jspb.JsClassTemplate.JS_RESERVED_WORDS.
52 | * @param {boolean=} opt_includeInstance Whether to include the JSPB instance
53 | * for transitional soy proto support: http://goto/soy-param-migration
54 | * @return {!Object}
55 | */
56 | proto.io.xtech.example.Movie.prototype.toObject = function(opt_includeInstance) {
57 | return proto.io.xtech.example.Movie.toObject(opt_includeInstance, this);
58 | };
59 |
60 |
61 | /**
62 | * Static version of the {@see toObject} method.
63 | * @param {boolean|undefined} includeInstance Whether to include the JSPB
64 | * instance for transitional soy proto support:
65 | * http://goto/soy-param-migration
66 | * @param {!proto.io.xtech.example.Movie} msg The msg instance to transform.
67 | * @return {!Object}
68 | * @suppress {unusedLocalVariables} f is only used for nested messages
69 | */
70 | proto.io.xtech.example.Movie.toObject = function(includeInstance, msg) {
71 | var f, obj = {
72 | name: jspb.Message.getFieldWithDefault(msg, 1, ""),
73 | year: jspb.Message.getFieldWithDefault(msg, 2, 0),
74 | rating: +jspb.Message.getFieldWithDefault(msg, 3, 0.0),
75 | castList: jspb.Message.getRepeatedField(msg, 4)
76 | };
77 |
78 | if (includeInstance) {
79 | obj.$jspbMessageInstance = msg;
80 | }
81 | return obj;
82 | };
83 | }
84 |
85 |
86 | /**
87 | * Deserializes binary data (in protobuf wire format).
88 | * @param {jspb.ByteSource} bytes The bytes to deserialize.
89 | * @return {!proto.io.xtech.example.Movie}
90 | */
91 | proto.io.xtech.example.Movie.deserializeBinary = function(bytes) {
92 | var reader = new jspb.BinaryReader(bytes);
93 | var msg = new proto.io.xtech.example.Movie;
94 | return proto.io.xtech.example.Movie.deserializeBinaryFromReader(msg, reader);
95 | };
96 |
97 |
98 | /**
99 | * Deserializes binary data (in protobuf wire format) from the
100 | * given reader into the given message object.
101 | * @param {!proto.io.xtech.example.Movie} msg The message object to deserialize into.
102 | * @param {!jspb.BinaryReader} reader The BinaryReader to use.
103 | * @return {!proto.io.xtech.example.Movie}
104 | */
105 | proto.io.xtech.example.Movie.deserializeBinaryFromReader = function(msg, reader) {
106 | while (reader.nextField()) {
107 | if (reader.isEndGroup()) {
108 | break;
109 | }
110 | var field = reader.getFieldNumber();
111 | switch (field) {
112 | case 1:
113 | var value = /** @type {string} */ (reader.readString());
114 | msg.setName(value);
115 | break;
116 | case 2:
117 | var value = /** @type {number} */ (reader.readInt32());
118 | msg.setYear(value);
119 | break;
120 | case 3:
121 | var value = /** @type {number} */ (reader.readFloat());
122 | msg.setRating(value);
123 | break;
124 | case 4:
125 | var value = /** @type {string} */ (reader.readString());
126 | msg.addCast(value);
127 | break;
128 | default:
129 | reader.skipField();
130 | break;
131 | }
132 | }
133 | return msg;
134 | };
135 |
136 |
137 | /**
138 | * Serializes the message to binary data (in protobuf wire format).
139 | * @return {!Uint8Array}
140 | */
141 | proto.io.xtech.example.Movie.prototype.serializeBinary = function() {
142 | var writer = new jspb.BinaryWriter();
143 | proto.io.xtech.example.Movie.serializeBinaryToWriter(this, writer);
144 | return writer.getResultBuffer();
145 | };
146 |
147 |
148 | /**
149 | * Serializes the given message to binary data (in protobuf wire
150 | * format), writing to the given BinaryWriter.
151 | * @param {!proto.io.xtech.example.Movie} message
152 | * @param {!jspb.BinaryWriter} writer
153 | * @suppress {unusedLocalVariables} f is only used for nested messages
154 | */
155 | proto.io.xtech.example.Movie.serializeBinaryToWriter = function(message, writer) {
156 | var f = undefined;
157 | f = message.getName();
158 | if (f.length > 0) {
159 | writer.writeString(
160 | 1,
161 | f
162 | );
163 | }
164 | f = message.getYear();
165 | if (f !== 0) {
166 | writer.writeInt32(
167 | 2,
168 | f
169 | );
170 | }
171 | f = message.getRating();
172 | if (f !== 0.0) {
173 | writer.writeFloat(
174 | 3,
175 | f
176 | );
177 | }
178 | f = message.getCastList();
179 | if (f.length > 0) {
180 | writer.writeRepeatedString(
181 | 4,
182 | f
183 | );
184 | }
185 | };
186 |
187 |
188 | /**
189 | * optional string name = 1;
190 | * @return {string}
191 | */
192 | proto.io.xtech.example.Movie.prototype.getName = function() {
193 | return /** @type {string} */ (jspb.Message.getFieldWithDefault(this, 1, ""));
194 | };
195 |
196 |
197 | /** @param {string} value */
198 | proto.io.xtech.example.Movie.prototype.setName = function(value) {
199 | jspb.Message.setField(this, 1, value);
200 | };
201 |
202 |
203 | /**
204 | * optional int32 year = 2;
205 | * @return {number}
206 | */
207 | proto.io.xtech.example.Movie.prototype.getYear = function() {
208 | return /** @type {number} */ (jspb.Message.getFieldWithDefault(this, 2, 0));
209 | };
210 |
211 |
212 | /** @param {number} value */
213 | proto.io.xtech.example.Movie.prototype.setYear = function(value) {
214 | jspb.Message.setField(this, 2, value);
215 | };
216 |
217 |
218 | /**
219 | * optional float rating = 3;
220 | * @return {number}
221 | */
222 | proto.io.xtech.example.Movie.prototype.getRating = function() {
223 | return /** @type {number} */ (+jspb.Message.getFieldWithDefault(this, 3, 0.0));
224 | };
225 |
226 |
227 | /** @param {number} value */
228 | proto.io.xtech.example.Movie.prototype.setRating = function(value) {
229 | jspb.Message.setField(this, 3, value);
230 | };
231 |
232 |
233 | /**
234 | * repeated string cast = 4;
235 | * @return {!Array.}
236 | */
237 | proto.io.xtech.example.Movie.prototype.getCastList = function() {
238 | return /** @type {!Array.} */ (jspb.Message.getRepeatedField(this, 4));
239 | };
240 |
241 |
242 | /** @param {!Array.} value */
243 | proto.io.xtech.example.Movie.prototype.setCastList = function(value) {
244 | jspb.Message.setField(this, 4, value || []);
245 | };
246 |
247 |
248 | /**
249 | * @param {!string} value
250 | * @param {number=} opt_index
251 | */
252 | proto.io.xtech.example.Movie.prototype.addCast = function(value, opt_index) {
253 | jspb.Message.addToRepeatedField(this, 4, value, opt_index);
254 | };
255 |
256 |
257 | proto.io.xtech.example.Movie.prototype.clearCastList = function() {
258 | this.setCastList([]);
259 | };
260 |
261 |
262 |
263 | /**
264 | * Generated by JsPbCodeGenerator.
265 | * @param {Array=} opt_data Optional initial data array, typically from a
266 | * server response, or constructed directly in Javascript. The array is used
267 | * in place and becomes part of the constructed object. It is not cloned.
268 | * If no data is provided, the constructed object will be empty, but still
269 | * valid.
270 | * @extends {jspb.Message}
271 | * @constructor
272 | */
273 | proto.io.xtech.example.EmptyRequest = function(opt_data) {
274 | jspb.Message.initialize(this, opt_data, 0, -1, null, null);
275 | };
276 | goog.inherits(proto.io.xtech.example.EmptyRequest, jspb.Message);
277 | if (goog.DEBUG && !COMPILED) {
278 | proto.io.xtech.example.EmptyRequest.displayName = 'proto.io.xtech.example.EmptyRequest';
279 | }
280 |
281 |
282 | if (jspb.Message.GENERATE_TO_OBJECT) {
283 | /**
284 | * Creates an object representation of this proto suitable for use in Soy templates.
285 | * Field names that are reserved in JavaScript and will be renamed to pb_name.
286 | * To access a reserved field use, foo.pb_, eg, foo.pb_default.
287 | * For the list of reserved names please see:
288 | * com.google.apps.jspb.JsClassTemplate.JS_RESERVED_WORDS.
289 | * @param {boolean=} opt_includeInstance Whether to include the JSPB instance
290 | * for transitional soy proto support: http://goto/soy-param-migration
291 | * @return {!Object}
292 | */
293 | proto.io.xtech.example.EmptyRequest.prototype.toObject = function(opt_includeInstance) {
294 | return proto.io.xtech.example.EmptyRequest.toObject(opt_includeInstance, this);
295 | };
296 |
297 |
298 | /**
299 | * Static version of the {@see toObject} method.
300 | * @param {boolean|undefined} includeInstance Whether to include the JSPB
301 | * instance for transitional soy proto support:
302 | * http://goto/soy-param-migration
303 | * @param {!proto.io.xtech.example.EmptyRequest} msg The msg instance to transform.
304 | * @return {!Object}
305 | * @suppress {unusedLocalVariables} f is only used for nested messages
306 | */
307 | proto.io.xtech.example.EmptyRequest.toObject = function(includeInstance, msg) {
308 | var f, obj = {
309 |
310 | };
311 |
312 | if (includeInstance) {
313 | obj.$jspbMessageInstance = msg;
314 | }
315 | return obj;
316 | };
317 | }
318 |
319 |
320 | /**
321 | * Deserializes binary data (in protobuf wire format).
322 | * @param {jspb.ByteSource} bytes The bytes to deserialize.
323 | * @return {!proto.io.xtech.example.EmptyRequest}
324 | */
325 | proto.io.xtech.example.EmptyRequest.deserializeBinary = function(bytes) {
326 | var reader = new jspb.BinaryReader(bytes);
327 | var msg = new proto.io.xtech.example.EmptyRequest;
328 | return proto.io.xtech.example.EmptyRequest.deserializeBinaryFromReader(msg, reader);
329 | };
330 |
331 |
332 | /**
333 | * Deserializes binary data (in protobuf wire format) from the
334 | * given reader into the given message object.
335 | * @param {!proto.io.xtech.example.EmptyRequest} msg The message object to deserialize into.
336 | * @param {!jspb.BinaryReader} reader The BinaryReader to use.
337 | * @return {!proto.io.xtech.example.EmptyRequest}
338 | */
339 | proto.io.xtech.example.EmptyRequest.deserializeBinaryFromReader = function(msg, reader) {
340 | while (reader.nextField()) {
341 | if (reader.isEndGroup()) {
342 | break;
343 | }
344 | var field = reader.getFieldNumber();
345 | switch (field) {
346 | default:
347 | reader.skipField();
348 | break;
349 | }
350 | }
351 | return msg;
352 | };
353 |
354 |
355 | /**
356 | * Serializes the message to binary data (in protobuf wire format).
357 | * @return {!Uint8Array}
358 | */
359 | proto.io.xtech.example.EmptyRequest.prototype.serializeBinary = function() {
360 | var writer = new jspb.BinaryWriter();
361 | proto.io.xtech.example.EmptyRequest.serializeBinaryToWriter(this, writer);
362 | return writer.getResultBuffer();
363 | };
364 |
365 |
366 | /**
367 | * Serializes the given message to binary data (in protobuf wire
368 | * format), writing to the given BinaryWriter.
369 | * @param {!proto.io.xtech.example.EmptyRequest} message
370 | * @param {!jspb.BinaryWriter} writer
371 | * @suppress {unusedLocalVariables} f is only used for nested messages
372 | */
373 | proto.io.xtech.example.EmptyRequest.serializeBinaryToWriter = function(message, writer) {
374 | var f = undefined;
375 | };
376 |
377 |
378 |
379 | /**
380 | * Generated by JsPbCodeGenerator.
381 | * @param {Array=} opt_data Optional initial data array, typically from a
382 | * server response, or constructed directly in Javascript. The array is used
383 | * in place and becomes part of the constructed object. It is not cloned.
384 | * If no data is provided, the constructed object will be empty, but still
385 | * valid.
386 | * @extends {jspb.Message}
387 | * @constructor
388 | */
389 | proto.io.xtech.example.SearchByCastInput = function(opt_data) {
390 | jspb.Message.initialize(this, opt_data, 0, -1, null, null);
391 | };
392 | goog.inherits(proto.io.xtech.example.SearchByCastInput, jspb.Message);
393 | if (goog.DEBUG && !COMPILED) {
394 | proto.io.xtech.example.SearchByCastInput.displayName = 'proto.io.xtech.example.SearchByCastInput';
395 | }
396 |
397 |
398 | if (jspb.Message.GENERATE_TO_OBJECT) {
399 | /**
400 | * Creates an object representation of this proto suitable for use in Soy templates.
401 | * Field names that are reserved in JavaScript and will be renamed to pb_name.
402 | * To access a reserved field use, foo.pb_, eg, foo.pb_default.
403 | * For the list of reserved names please see:
404 | * com.google.apps.jspb.JsClassTemplate.JS_RESERVED_WORDS.
405 | * @param {boolean=} opt_includeInstance Whether to include the JSPB instance
406 | * for transitional soy proto support: http://goto/soy-param-migration
407 | * @return {!Object}
408 | */
409 | proto.io.xtech.example.SearchByCastInput.prototype.toObject = function(opt_includeInstance) {
410 | return proto.io.xtech.example.SearchByCastInput.toObject(opt_includeInstance, this);
411 | };
412 |
413 |
414 | /**
415 | * Static version of the {@see toObject} method.
416 | * @param {boolean|undefined} includeInstance Whether to include the JSPB
417 | * instance for transitional soy proto support:
418 | * http://goto/soy-param-migration
419 | * @param {!proto.io.xtech.example.SearchByCastInput} msg The msg instance to transform.
420 | * @return {!Object}
421 | * @suppress {unusedLocalVariables} f is only used for nested messages
422 | */
423 | proto.io.xtech.example.SearchByCastInput.toObject = function(includeInstance, msg) {
424 | var f, obj = {
425 | castname: jspb.Message.getFieldWithDefault(msg, 1, "")
426 | };
427 |
428 | if (includeInstance) {
429 | obj.$jspbMessageInstance = msg;
430 | }
431 | return obj;
432 | };
433 | }
434 |
435 |
436 | /**
437 | * Deserializes binary data (in protobuf wire format).
438 | * @param {jspb.ByteSource} bytes The bytes to deserialize.
439 | * @return {!proto.io.xtech.example.SearchByCastInput}
440 | */
441 | proto.io.xtech.example.SearchByCastInput.deserializeBinary = function(bytes) {
442 | var reader = new jspb.BinaryReader(bytes);
443 | var msg = new proto.io.xtech.example.SearchByCastInput;
444 | return proto.io.xtech.example.SearchByCastInput.deserializeBinaryFromReader(msg, reader);
445 | };
446 |
447 |
448 | /**
449 | * Deserializes binary data (in protobuf wire format) from the
450 | * given reader into the given message object.
451 | * @param {!proto.io.xtech.example.SearchByCastInput} msg The message object to deserialize into.
452 | * @param {!jspb.BinaryReader} reader The BinaryReader to use.
453 | * @return {!proto.io.xtech.example.SearchByCastInput}
454 | */
455 | proto.io.xtech.example.SearchByCastInput.deserializeBinaryFromReader = function(msg, reader) {
456 | while (reader.nextField()) {
457 | if (reader.isEndGroup()) {
458 | break;
459 | }
460 | var field = reader.getFieldNumber();
461 | switch (field) {
462 | case 1:
463 | var value = /** @type {string} */ (reader.readString());
464 | msg.setCastname(value);
465 | break;
466 | default:
467 | reader.skipField();
468 | break;
469 | }
470 | }
471 | return msg;
472 | };
473 |
474 |
475 | /**
476 | * Serializes the message to binary data (in protobuf wire format).
477 | * @return {!Uint8Array}
478 | */
479 | proto.io.xtech.example.SearchByCastInput.prototype.serializeBinary = function() {
480 | var writer = new jspb.BinaryWriter();
481 | proto.io.xtech.example.SearchByCastInput.serializeBinaryToWriter(this, writer);
482 | return writer.getResultBuffer();
483 | };
484 |
485 |
486 | /**
487 | * Serializes the given message to binary data (in protobuf wire
488 | * format), writing to the given BinaryWriter.
489 | * @param {!proto.io.xtech.example.SearchByCastInput} message
490 | * @param {!jspb.BinaryWriter} writer
491 | * @suppress {unusedLocalVariables} f is only used for nested messages
492 | */
493 | proto.io.xtech.example.SearchByCastInput.serializeBinaryToWriter = function(message, writer) {
494 | var f = undefined;
495 | f = message.getCastname();
496 | if (f.length > 0) {
497 | writer.writeString(
498 | 1,
499 | f
500 | );
501 | }
502 | };
503 |
504 |
505 | /**
506 | * optional string castName = 1;
507 | * @return {string}
508 | */
509 | proto.io.xtech.example.SearchByCastInput.prototype.getCastname = function() {
510 | return /** @type {string} */ (jspb.Message.getFieldWithDefault(this, 1, ""));
511 | };
512 |
513 |
514 | /** @param {string} value */
515 | proto.io.xtech.example.SearchByCastInput.prototype.setCastname = function(value) {
516 | jspb.Message.setField(this, 1, value);
517 | };
518 |
519 |
520 |
521 | /**
522 | * Generated by JsPbCodeGenerator.
523 | * @param {Array=} opt_data Optional initial data array, typically from a
524 | * server response, or constructed directly in Javascript. The array is used
525 | * in place and becomes part of the constructed object. It is not cloned.
526 | * If no data is provided, the constructed object will be empty, but still
527 | * valid.
528 | * @extends {jspb.Message}
529 | * @constructor
530 | */
531 | proto.io.xtech.example.MoviesResult = function(opt_data) {
532 | jspb.Message.initialize(this, opt_data, 0, -1, proto.io.xtech.example.MoviesResult.repeatedFields_, null);
533 | };
534 | goog.inherits(proto.io.xtech.example.MoviesResult, jspb.Message);
535 | if (goog.DEBUG && !COMPILED) {
536 | proto.io.xtech.example.MoviesResult.displayName = 'proto.io.xtech.example.MoviesResult';
537 | }
538 | /**
539 | * List of repeated fields within this message type.
540 | * @private {!Array}
541 | * @const
542 | */
543 | proto.io.xtech.example.MoviesResult.repeatedFields_ = [1];
544 |
545 |
546 |
547 | if (jspb.Message.GENERATE_TO_OBJECT) {
548 | /**
549 | * Creates an object representation of this proto suitable for use in Soy templates.
550 | * Field names that are reserved in JavaScript and will be renamed to pb_name.
551 | * To access a reserved field use, foo.pb_, eg, foo.pb_default.
552 | * For the list of reserved names please see:
553 | * com.google.apps.jspb.JsClassTemplate.JS_RESERVED_WORDS.
554 | * @param {boolean=} opt_includeInstance Whether to include the JSPB instance
555 | * for transitional soy proto support: http://goto/soy-param-migration
556 | * @return {!Object}
557 | */
558 | proto.io.xtech.example.MoviesResult.prototype.toObject = function(opt_includeInstance) {
559 | return proto.io.xtech.example.MoviesResult.toObject(opt_includeInstance, this);
560 | };
561 |
562 |
563 | /**
564 | * Static version of the {@see toObject} method.
565 | * @param {boolean|undefined} includeInstance Whether to include the JSPB
566 | * instance for transitional soy proto support:
567 | * http://goto/soy-param-migration
568 | * @param {!proto.io.xtech.example.MoviesResult} msg The msg instance to transform.
569 | * @return {!Object}
570 | * @suppress {unusedLocalVariables} f is only used for nested messages
571 | */
572 | proto.io.xtech.example.MoviesResult.toObject = function(includeInstance, msg) {
573 | var f, obj = {
574 | resultList: jspb.Message.toObjectList(msg.getResultList(),
575 | proto.io.xtech.example.Movie.toObject, includeInstance)
576 | };
577 |
578 | if (includeInstance) {
579 | obj.$jspbMessageInstance = msg;
580 | }
581 | return obj;
582 | };
583 | }
584 |
585 |
586 | /**
587 | * Deserializes binary data (in protobuf wire format).
588 | * @param {jspb.ByteSource} bytes The bytes to deserialize.
589 | * @return {!proto.io.xtech.example.MoviesResult}
590 | */
591 | proto.io.xtech.example.MoviesResult.deserializeBinary = function(bytes) {
592 | var reader = new jspb.BinaryReader(bytes);
593 | var msg = new proto.io.xtech.example.MoviesResult;
594 | return proto.io.xtech.example.MoviesResult.deserializeBinaryFromReader(msg, reader);
595 | };
596 |
597 |
598 | /**
599 | * Deserializes binary data (in protobuf wire format) from the
600 | * given reader into the given message object.
601 | * @param {!proto.io.xtech.example.MoviesResult} msg The message object to deserialize into.
602 | * @param {!jspb.BinaryReader} reader The BinaryReader to use.
603 | * @return {!proto.io.xtech.example.MoviesResult}
604 | */
605 | proto.io.xtech.example.MoviesResult.deserializeBinaryFromReader = function(msg, reader) {
606 | while (reader.nextField()) {
607 | if (reader.isEndGroup()) {
608 | break;
609 | }
610 | var field = reader.getFieldNumber();
611 | switch (field) {
612 | case 1:
613 | var value = new proto.io.xtech.example.Movie;
614 | reader.readMessage(value,proto.io.xtech.example.Movie.deserializeBinaryFromReader);
615 | msg.addResult(value);
616 | break;
617 | default:
618 | reader.skipField();
619 | break;
620 | }
621 | }
622 | return msg;
623 | };
624 |
625 |
626 | /**
627 | * Serializes the message to binary data (in protobuf wire format).
628 | * @return {!Uint8Array}
629 | */
630 | proto.io.xtech.example.MoviesResult.prototype.serializeBinary = function() {
631 | var writer = new jspb.BinaryWriter();
632 | proto.io.xtech.example.MoviesResult.serializeBinaryToWriter(this, writer);
633 | return writer.getResultBuffer();
634 | };
635 |
636 |
637 | /**
638 | * Serializes the given message to binary data (in protobuf wire
639 | * format), writing to the given BinaryWriter.
640 | * @param {!proto.io.xtech.example.MoviesResult} message
641 | * @param {!jspb.BinaryWriter} writer
642 | * @suppress {unusedLocalVariables} f is only used for nested messages
643 | */
644 | proto.io.xtech.example.MoviesResult.serializeBinaryToWriter = function(message, writer) {
645 | var f = undefined;
646 | f = message.getResultList();
647 | if (f.length > 0) {
648 | writer.writeRepeatedMessage(
649 | 1,
650 | f,
651 | proto.io.xtech.example.Movie.serializeBinaryToWriter
652 | );
653 | }
654 | };
655 |
656 |
657 | /**
658 | * repeated Movie result = 1;
659 | * @return {!Array.}
660 | */
661 | proto.io.xtech.example.MoviesResult.prototype.getResultList = function() {
662 | return /** @type{!Array.} */ (
663 | jspb.Message.getRepeatedWrapperField(this, proto.io.xtech.example.Movie, 1));
664 | };
665 |
666 |
667 | /** @param {!Array.} value */
668 | proto.io.xtech.example.MoviesResult.prototype.setResultList = function(value) {
669 | jspb.Message.setRepeatedWrapperField(this, 1, value);
670 | };
671 |
672 |
673 | /**
674 | * @param {!proto.io.xtech.example.Movie=} opt_value
675 | * @param {number=} opt_index
676 | * @return {!proto.io.xtech.example.Movie}
677 | */
678 | proto.io.xtech.example.MoviesResult.prototype.addResult = function(opt_value, opt_index) {
679 | return jspb.Message.addToRepeatedWrapperField(this, 1, opt_value, proto.io.xtech.example.Movie, opt_index);
680 | };
681 |
682 |
683 | proto.io.xtech.example.MoviesResult.prototype.clearResultList = function() {
684 | this.setResultList([]);
685 | };
686 |
687 |
688 | goog.object.extend(exports, proto.io.xtech.example);
689 |
--------------------------------------------------------------------------------
/example/grpc/src/server.ts:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env node
2 |
3 | import * as debug from "debug";
4 | import * as grpc from "grpc";
5 |
6 | import { ExampleService, IExampleServer } from "./proto/Example_grpc_pb";
7 | import { EmptyRequest, Movie, MoviesResult, SearchByCastInput } from "./proto/Example_pb";
8 |
9 | const log = debug("SampleServer");
10 |
11 | interface IRawMovie {
12 | cast: string[];
13 | name: string;
14 | rating: number;
15 | year: number;
16 | }
17 |
18 | const Movies = [
19 | {
20 | cast: ["Tom Cruise", "Simon Pegg", "Jeremy Renner"],
21 | name: "Mission: Impossible Rogue Nation",
22 | rating: 0.97,
23 | year: 2015,
24 | },
25 | {
26 | cast: ["Tom Cruise", "Simon Pegg", "Henry Cavill"],
27 | name: "Mission: Impossible - Fallout",
28 | rating: 0.93,
29 | year: 2018,
30 | },
31 | {
32 | cast: ["Leonardo DiCaprio", "Jonah Hill", "Margot Robbie"],
33 | name: "The Wolf of Wall Street",
34 | rating: 0.78,
35 | year: 2013,
36 | },
37 | ];
38 |
39 | function createMovie(movie: IRawMovie): Movie {
40 | const result = new Movie();
41 |
42 | result.setCastList(movie.cast);
43 | result.setName(movie.name);
44 | result.setYear(movie.year);
45 | result.setRating(movie.rating);
46 |
47 | return result;
48 | }
49 |
50 | class ServerImpl implements IExampleServer {
51 | public getMovies(request: grpc.ServerUnaryCall, callback: grpc.sendUnaryData) {
52 | const result = new MoviesResult();
53 | Movies.map(createMovie).forEach((movie: Movie) => result.addResult(movie));
54 | callback(null, result);
55 | }
56 |
57 | public searchMoviesByCast(call: grpc.ServerWriteableStream) {
58 | log("call started");
59 | const input: SearchByCastInput = call.request;
60 | let i: number = 1;
61 | call.on("error", (error) => {
62 | log(error);
63 | call.end();
64 | });
65 | Movies.map(createMovie).forEach((movie: Movie) => {
66 | if (movie.getCastList().indexOf(input.getCastname()) > -1) {
67 | setTimeout(() => {
68 | log(movie.getName());
69 | call.write(movie);
70 | }, i * 1000);
71 | i += 1;
72 | }
73 | });
74 | setTimeout(() => {
75 | call.end();
76 | log("call ended");
77 | }, 3000);
78 | }
79 | }
80 |
81 | function startServer() {
82 | const server = new grpc.Server();
83 |
84 | server.addService(ExampleService, new ServerImpl());
85 | server.bind("0.0.0.0:50051", grpc.ServerCredentials.createInsecure());
86 | server.start();
87 |
88 | log("Server started, listening: 0.0.0.0:50051");
89 | }
90 |
91 | startServer();
92 |
93 | process.on("uncaughtException", (err) => {
94 | log(`process on uncaughtException error: ${err}`);
95 | });
96 |
97 | process.on("unhandledRejection", (err) => {
98 | log(`process on unhandledRejection error: ${err}`);
99 | });
100 |
--------------------------------------------------------------------------------
/example/grpc/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "compilerOptions": {
3 | "lib": [
4 | "es2015",
5 | "esnext.asynciterable"
6 | ],
7 | "target": "ES6",
8 | "module": "commonjs",
9 | "sourceMap": true,
10 | "declaration": true,
11 | "rootDir": "src",
12 | "outDir": "build",
13 | "experimentalDecorators": true,
14 | "emitDecoratorMetadata": true
15 | },
16 | "include": [
17 | "src/*"
18 | ],
19 | "exclude": [
20 | "node_modules"
21 | ]
22 | }
--------------------------------------------------------------------------------
/example/grpc/tslint.json:
--------------------------------------------------------------------------------
1 | {
2 | "defaultSeverity": "error",
3 | "extends": [
4 | "tslint:recommended"
5 | ],
6 | "jsRules": {},
7 | "rules": {},
8 | "rulesDirectory": []
9 | }
--------------------------------------------------------------------------------
/example/index.js:
--------------------------------------------------------------------------------
1 | const path = require('path');
2 | const { GraphQLServer, PubSub } = require('graphql-yoga');
3 | const { printSchema } = require('graphql');
4 | const { getGraphqlSchemaFromGrpc } = require('grpc-graphql-schema');
5 |
6 | getGraphqlSchemaFromGrpc({
7 | endpoint: 'localhost:50051',
8 | protoFilePath: path.resolve(__dirname, 'grpc', 'proto', 'Example.proto'),
9 | serviceName: 'Example',
10 | packageName: 'io.xtech.example',
11 | }).then((schema) => {
12 | console.log(printSchema(schema));
13 | const pubsub = new PubSub();
14 | const server = new GraphQLServer({
15 | schema,
16 | context: {
17 | pubsub,
18 | },
19 | });
20 | server.start({
21 | port: 4000,
22 | }, () => console.log('server started on port 4000'));
23 | });
--------------------------------------------------------------------------------
/example/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "grpc-graphql-schema-example",
3 | "version": "1.0.0",
4 | "main": "index.js",
5 | "author": "Simon Liang",
6 | "license": "MIT",
7 | "private": false,
8 | "scripts": {
9 | "start": "node ."
10 | },
11 | "dependencies": {
12 | "graphql": "^14.0.2",
13 | "graphql-tools": "^4.0.3",
14 | "graphql-yoga": "^1.16.9",
15 | "grpc-graphql-schema": "^0.0.7"
16 | }
17 | }
18 |
--------------------------------------------------------------------------------
/example/schema.graphql:
--------------------------------------------------------------------------------
1 | type Movie {
2 | name: String
3 | year: Int
4 | rating: Float
5 | cast: [String]
6 | }
7 |
8 | type MoviesResult {
9 | result: [Movie]
10 | }
11 |
12 | type Query {
13 | ping: ServerStatus
14 | ExampleGetMovies: MoviesResult
15 | }
16 |
17 | input SearchByCastInput {
18 | castName: String
19 | }
20 |
21 | type ServerStatus {
22 | status: String
23 | }
24 |
25 | type Subscription {
26 | ExampleSearchMoviesByCast(SearchByCastInput: SearchByCastInput): Movie
27 | }
--------------------------------------------------------------------------------
/grpcgraphql.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/xanthous-tech/grpc-graphql-schema/06c97e7a879045ba81f499aade9409048297cf8f/grpcgraphql.png
--------------------------------------------------------------------------------
/lib/index.d.ts:
--------------------------------------------------------------------------------
1 | import { GraphQLSchema } from 'graphql';
2 | import { GrpcGraphqlSchemaConfiguration } from './types';
3 | export { getGraphqlQueriesFromProtoService, getGraphqlMutationsFromProtoService, getGraphQlSubscriptionsFromProtoService, } from './service_converter';
4 | export { convertGrpcTypeToGraphqlType, getGraphqlTypeFromProtoDefinition, } from './type_converter';
5 | export { GRPC_GQL_TYPE_MAPPING, GrpcGraphqlSchemaConfiguration, typeDefinitionCache, } from './types';
6 | export declare function getGraphqlSchemaFromGrpc({ endpoint, protoFilePath, serviceName, packageName, }: GrpcGraphqlSchemaConfiguration): Promise;
7 |
--------------------------------------------------------------------------------
/lib/index.js:
--------------------------------------------------------------------------------
1 | "use strict";
2 | var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3 | return new (P || (P = Promise))(function (resolve, reject) {
4 | function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5 | function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6 | function step(result) { result.done ? resolve(result.value) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); }
7 | step((generator = generator.apply(thisArg, _arguments || [])).next());
8 | });
9 | };
10 | Object.defineProperty(exports, "__esModule", { value: true });
11 | const grpcCaller = require("grpc-caller");
12 | const graphql_1 = require("graphql");
13 | const type_converter_1 = require("./type_converter");
14 | const service_converter_1 = require("./service_converter");
15 | const protobuf_1 = require("./protobuf");
16 | var service_converter_2 = require("./service_converter");
17 | exports.getGraphqlQueriesFromProtoService = service_converter_2.getGraphqlQueriesFromProtoService;
18 | exports.getGraphqlMutationsFromProtoService = service_converter_2.getGraphqlMutationsFromProtoService;
19 | exports.getGraphQlSubscriptionsFromProtoService = service_converter_2.getGraphQlSubscriptionsFromProtoService;
20 | var type_converter_2 = require("./type_converter");
21 | exports.convertGrpcTypeToGraphqlType = type_converter_2.convertGrpcTypeToGraphqlType;
22 | exports.getGraphqlTypeFromProtoDefinition = type_converter_2.getGraphqlTypeFromProtoDefinition;
23 | var types_1 = require("./types");
24 | exports.GRPC_GQL_TYPE_MAPPING = types_1.GRPC_GQL_TYPE_MAPPING;
25 | exports.typeDefinitionCache = types_1.typeDefinitionCache;
26 | function getGraphqlSchemaFromGrpc({ endpoint, protoFilePath, serviceName, packageName, }) {
27 | return __awaiter(this, void 0, void 0, function* () {
28 | const client = grpcCaller(endpoint, protoFilePath, serviceName, null, {
29 | 'grpc.max_send_message_length': -1,
30 | 'grpc.max_receive_message_length': -1,
31 | });
32 | const { nested } = yield protobuf_1.getPackageProtoDefinition(protoFilePath, packageName);
33 | const types = Object.keys(nested)
34 | .filter((key) => 'fields' in nested[key])
35 | .reduce((acc, key) => {
36 | const definition = nested[key];
37 | // skip empty
38 | if (key.startsWith('Empty')) {
39 | return acc;
40 | }
41 | if (definition.fields) {
42 | return acc.concat([
43 | type_converter_1.getGraphqlTypeFromProtoDefinition({
44 | definition: definition,
45 | typeName: key,
46 | }),
47 | ]);
48 | }
49 | return acc;
50 | }, []);
51 | const query = Object.keys(nested)
52 | .filter((key) => 'methods' in nested[key] && key === serviceName)
53 | .reduce((__, key) => {
54 | const definition = nested[key];
55 | return service_converter_1.getGraphqlQueriesFromProtoService({
56 | client,
57 | definition,
58 | serviceName: key,
59 | });
60 | }, null);
61 | const mutation = Object.keys(nested)
62 | .filter((key) => 'methods' in nested[key] && key === serviceName)
63 | .reduce((__, key) => {
64 | const definition = nested[key];
65 | return service_converter_1.getGraphqlMutationsFromProtoService({
66 | client,
67 | definition,
68 | serviceName: key,
69 | });
70 | }, null);
71 | const subscription = Object.keys(nested)
72 | .filter(key => 'methods' in nested[key] && key === serviceName)
73 | .reduce((__, key) => {
74 | const definition = nested[key];
75 | return service_converter_1.getGraphQlSubscriptionsFromProtoService({
76 | client,
77 | definition,
78 | serviceName: key,
79 | });
80 | }, null);
81 | return new graphql_1.GraphQLSchema({
82 | types,
83 | query,
84 | mutation,
85 | subscription,
86 | });
87 | });
88 | }
89 | exports.getGraphqlSchemaFromGrpc = getGraphqlSchemaFromGrpc;
90 | //# sourceMappingURL=index.js.map
--------------------------------------------------------------------------------
/lib/index.js.map:
--------------------------------------------------------------------------------
1 | {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
--------------------------------------------------------------------------------
/lib/protobuf.d.ts:
--------------------------------------------------------------------------------
1 | import * as protobuf from 'protobufjs';
2 | export declare function getPackageProtoDefinition(protoFile: string, packageName: string): Promise;
3 |
--------------------------------------------------------------------------------
/lib/protobuf.js:
--------------------------------------------------------------------------------
1 | "use strict";
2 | var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3 | return new (P || (P = Promise))(function (resolve, reject) {
4 | function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5 | function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6 | function step(result) { result.done ? resolve(result.value) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); }
7 | step((generator = generator.apply(thisArg, _arguments || [])).next());
8 | });
9 | };
10 | Object.defineProperty(exports, "__esModule", { value: true });
11 | const _ = require("lodash");
12 | const protobuf = require("protobufjs");
13 | function getPackageProtoDefinition(protoFile, packageName) {
14 | return __awaiter(this, void 0, void 0, function* () {
15 | const protoDefinition = yield protobuf.load(protoFile);
16 | const protoDefinitionObject = yield protoDefinition.toJSON({
17 | keepComments: true,
18 | });
19 | const packagePaths = packageName.split('.');
20 | for (let i = 0; i < packagePaths.length; i += 2) {
21 | packagePaths.splice(i, 0, 'nested');
22 | }
23 | return _.get(protoDefinitionObject, packagePaths.join('.'));
24 | });
25 | }
26 | exports.getPackageProtoDefinition = getPackageProtoDefinition;
27 | //# sourceMappingURL=protobuf.js.map
--------------------------------------------------------------------------------
/lib/protobuf.js.map:
--------------------------------------------------------------------------------
1 | {"version":3,"file":"protobuf.js","sourceRoot":"","sources":["../src/protobuf.ts"],"names":[],"mappings":";;;;;;;;;;AAAA,4BAA4B;AAC5B,uCAAuC;AAEvC,SAAsB,yBAAyB,CAC7C,SAAiB,EACjB,WAAmB;;QAEnB,MAAM,eAAe,GAAG,MAAM,QAAQ,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;QACvD,MAAM,qBAAqB,GAAG,MAAM,eAAe,CAAC,MAAM,CAAC;YACzD,YAAY,EAAE,IAAI;SACnB,CAAC,CAAC;QACH,MAAM,YAAY,GAAa,WAAW,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;QAEtD,KAAK,IAAI,CAAC,GAAW,CAAC,EAAE,CAAC,GAAG,YAAY,CAAC,MAAM,EAAE,CAAC,IAAI,CAAC,EAAE;YACvD,YAAY,CAAC,MAAM,CAAC,CAAC,EAAE,CAAC,EAAE,QAAQ,CAAC,CAAC;SACrC;QAED,OAAO,CAAC,CAAC,GAAG,CAAC,qBAAqB,EAAE,YAAY,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC;IAC9D,CAAC;CAAA;AAfD,8DAeC"}
--------------------------------------------------------------------------------
/lib/service_converter.d.ts:
--------------------------------------------------------------------------------
1 | import { GraphQLObjectType } from 'graphql';
2 | export declare function getGraphqlQueriesFromProtoService({ definition, serviceName, client, }: {
3 | definition: any;
4 | serviceName: any;
5 | client: any;
6 | }): GraphQLObjectType;
7 | export declare function getGraphqlMutationsFromProtoService({ definition, serviceName, client, }: {
8 | definition: any;
9 | serviceName: any;
10 | client: any;
11 | }): GraphQLObjectType;
12 | export declare function getGraphQlSubscriptionsFromProtoService({ definition, serviceName, client, }: {
13 | definition: any;
14 | serviceName: any;
15 | client: any;
16 | }): GraphQLObjectType;
17 |
--------------------------------------------------------------------------------
/lib/service_converter.js:
--------------------------------------------------------------------------------
1 | "use strict";
2 | var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3 | return new (P || (P = Promise))(function (resolve, reject) {
4 | function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5 | function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6 | function step(result) { result.done ? resolve(result.value) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); }
7 | step((generator = generator.apply(thisArg, _arguments || [])).next());
8 | });
9 | };
10 | Object.defineProperty(exports, "__esModule", { value: true });
11 | const _ = require("lodash");
12 | const graphql_1 = require("graphql");
13 | const subscription_1 = require("./subscription");
14 | const type_converter_1 = require("./type_converter");
15 | const types_1 = require("./types");
16 | function getGraphqlMethodsFromProtoService({ definition, serviceName, client, methodType, }) {
17 | const { methods } = definition;
18 | const fields = () => Object.keys(methods).reduce((result, methodName) => {
19 | const args = {};
20 | const { requestType: requestArgName, responseType, responseStream, comment, } = methods[methodName];
21 | if (responseStream) {
22 | // responseStream should be in subscriptions
23 | return result;
24 | }
25 | // filter for mutations
26 | if (methodType === 'Mutation' && !methodName.startsWith('Set')) {
27 | return result;
28 | }
29 | // filter out ping for mutation
30 | if (methodType === 'Mutation' && methodName === 'ping') {
31 | return result;
32 | }
33 | if (!requestArgName.startsWith('Empty')) {
34 | args[requestArgName] = {
35 | type: types_1.typeDefinitionCache[requestArgName],
36 | };
37 | }
38 | const queryField = {
39 | args,
40 | type: types_1.typeDefinitionCache[responseType],
41 | description: comment,
42 | resolve: (__, arg) => __awaiter(this, void 0, void 0, function* () {
43 | const response = yield client[methodName](arg[requestArgName] || {}, {}, {
44 | deadline: Date.now() + (Number(process.env.REQUEST_TIMEOUT) || 200000),
45 | });
46 | // FIXME: there is a bug in the graphQL type conversion
47 | return response;
48 | // return convertGrpcTypeToGraphqlType(
49 | // response,
50 | // typeDefinitionCache[responseType],
51 | // );
52 | }),
53 | };
54 | // eslint-disable-next-line no-param-reassign
55 | result[`${serviceName}${methodName}`] = queryField;
56 | return result;
57 | }, (methodType === 'Mutation') ? {} : {
58 | // adding a default ping
59 | ping: {
60 | type: types_1.typeDefinitionCache.ServerStatus,
61 | description: 'query for getting server status',
62 | resolve: () => ({ status: 'online' }),
63 | },
64 | });
65 | if (_.isEmpty(fields())) {
66 | return null;
67 | }
68 | return new graphql_1.GraphQLObjectType({
69 | fields,
70 | name: methodType,
71 | });
72 | }
73 | function getGraphqlQueriesFromProtoService({ definition, serviceName, client, }) {
74 | return getGraphqlMethodsFromProtoService({
75 | definition,
76 | serviceName,
77 | client,
78 | methodType: 'Query',
79 | });
80 | }
81 | exports.getGraphqlQueriesFromProtoService = getGraphqlQueriesFromProtoService;
82 | function getGraphqlMutationsFromProtoService({ definition, serviceName, client, }) {
83 | return getGraphqlMethodsFromProtoService({
84 | definition,
85 | serviceName,
86 | client,
87 | methodType: 'Mutation',
88 | });
89 | }
90 | exports.getGraphqlMutationsFromProtoService = getGraphqlMutationsFromProtoService;
91 | function getGraphQlSubscriptionsFromProtoService({ definition, serviceName, client, }) {
92 | const { methods } = definition;
93 | const fields = () => Object.keys(methods).reduce((result, methodName) => {
94 | const args = {};
95 | const { requestType: requestArgName, responseType, responseStream, comment, } = methods[methodName];
96 | if (!responseStream) {
97 | // non-responseStream should be in queries / mutations
98 | return result;
99 | }
100 | if (!requestArgName.startsWith('Empty')) {
101 | args[requestArgName] = {
102 | type: types_1.typeDefinitionCache[requestArgName],
103 | };
104 | }
105 | const subscribeField = {
106 | args,
107 | type: types_1.typeDefinitionCache[responseType],
108 | description: comment,
109 | subscribe: (__, arg, { pubsub }) => __awaiter(this, void 0, void 0, function* () {
110 | const response = yield client[methodName](arg[requestArgName] || {}, {});
111 | response.on('data', (data) => {
112 | const payload = {};
113 | payload[`${serviceName}${methodName}`] = type_converter_1.convertGrpcTypeToGraphqlType(data, types_1.typeDefinitionCache[responseType]);
114 | pubsub.publish(`${methodName}-onSubscribe`, payload);
115 | });
116 | response.on('error', (error) => {
117 | if (error.code === 1) {
118 | // cancelled
119 | response.removeAllListeners('error');
120 | response.removeAllListeners();
121 | }
122 | });
123 | response.on('end', () => {
124 | response.removeAllListeners();
125 | });
126 | const asyncIterator = pubsub.asyncIterator(`${methodName}-onSubscribe`);
127 | return subscription_1.withAsyncIteratorCancel(asyncIterator, () => {
128 | response.cancel();
129 | });
130 | }),
131 | };
132 | // eslint-disable-next-line no-param-reassign
133 | result[`${serviceName}${methodName}`] = subscribeField;
134 | return result;
135 | }, {});
136 | if (_.isEmpty(fields())) {
137 | return null;
138 | }
139 | return new graphql_1.GraphQLObjectType({
140 | fields,
141 | name: 'Subscription',
142 | });
143 | }
144 | exports.getGraphQlSubscriptionsFromProtoService = getGraphQlSubscriptionsFromProtoService;
145 | //# sourceMappingURL=service_converter.js.map
--------------------------------------------------------------------------------
/lib/service_converter.js.map:
--------------------------------------------------------------------------------
1 | {"version":3,"file":"service_converter.js","sourceRoot":"","sources":["../src/service_converter.ts"],"names":[],"mappings":"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"}
--------------------------------------------------------------------------------
/lib/subscription.d.ts:
--------------------------------------------------------------------------------
1 | export declare function withAsyncIteratorCancel(asyncIterator: any, onCancel: any): any;
2 |
--------------------------------------------------------------------------------
/lib/subscription.js:
--------------------------------------------------------------------------------
1 | "use strict";
2 | Object.defineProperty(exports, "__esModule", { value: true });
3 | // https://github.com/apollographql/graphql-subscriptions/issues/99#issuecomment-400500956
4 | function withAsyncIteratorCancel(asyncIterator, onCancel) {
5 | return Object.assign({}, asyncIterator, { return() {
6 | if (typeof onCancel === 'function') {
7 | onCancel();
8 | }
9 | return asyncIterator.return
10 | ? asyncIterator.return()
11 | : Promise.resolve({ value: undefined, done: true });
12 | } });
13 | }
14 | exports.withAsyncIteratorCancel = withAsyncIteratorCancel;
15 | //# sourceMappingURL=subscription.js.map
--------------------------------------------------------------------------------
/lib/subscription.js.map:
--------------------------------------------------------------------------------
1 | {"version":3,"file":"subscription.js","sourceRoot":"","sources":["../src/subscription.ts"],"names":[],"mappings":";;AAAA,0FAA0F;AAC1F,SAAgB,uBAAuB,CAAC,aAAa,EAAE,QAAQ;IAC7D,yBACK,aAAa,IAChB,MAAM;YACJ,IAAI,OAAO,QAAQ,KAAK,UAAU,EAAE;gBAClC,QAAQ,EAAE,CAAC;aACZ;YACD,OAAO,aAAa,CAAC,MAAM;gBACzB,CAAC,CAAC,aAAa,CAAC,MAAM,EAAE;gBACxB,CAAC,CAAC,OAAO,CAAC,OAAO,CAAC,EAAE,KAAK,EAAE,SAAS,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC,CAAC;QACxD,CAAC,IACD;AACJ,CAAC;AAZD,0DAYC"}
--------------------------------------------------------------------------------
/lib/type_converter.d.ts:
--------------------------------------------------------------------------------
1 | import * as protobuf from 'protobufjs';
2 | import { GraphQLInputObjectType, GraphQLObjectType } from 'graphql';
3 | interface IFieldWithComment extends protobuf.IField {
4 | comment?: string | null | undefined;
5 | }
6 | interface ITypeWithComment extends protobuf.IType {
7 | fields: {
8 | [k: string]: IFieldWithComment;
9 | };
10 | comment?: string | null | undefined;
11 | }
12 | interface ProtoDefinitionInput {
13 | definition: ITypeWithComment;
14 | typeName: string;
15 | }
16 | export declare function convertGrpcTypeToGraphqlType(payload: any, typeDef: any): any;
17 | export declare function getGraphqlTypeFromProtoDefinition({ definition, typeName }: ProtoDefinitionInput): GraphQLInputObjectType | GraphQLObjectType;
18 | export {};
19 |
--------------------------------------------------------------------------------
/lib/type_converter.js:
--------------------------------------------------------------------------------
1 | "use strict";
2 | Object.defineProperty(exports, "__esModule", { value: true });
3 | const Long = require("long");
4 | const graphql_1 = require("graphql");
5 | const types_1 = require("./types");
6 | function convertToGraphqlType(value) {
7 | if (Long.isLong(value)) {
8 | // conver long
9 | return value.toNumber();
10 | }
11 | return value;
12 | }
13 | // TODO: this convert method is not complete
14 | function convertGrpcTypeToGraphqlType(payload, typeDef) {
15 | const fields = typeDef.getFields();
16 | Object.keys(fields).forEach((key) => {
17 | const value = payload[key];
18 | const field = fields[key];
19 | const fieldType = field.type;
20 | if (graphql_1.isListType(fieldType)) {
21 | // process list
22 | // eslint-disable-next-line no-param-reassign
23 | payload[key] = value.map(convertToGraphqlType);
24 | }
25 | else {
26 | // eslint-disable-next-line no-param-reassign
27 | payload[key] = convertToGraphqlType(value);
28 | }
29 | });
30 | return payload;
31 | }
32 | exports.convertGrpcTypeToGraphqlType = convertGrpcTypeToGraphqlType;
33 | function getGraphqlTypeFromProtoDefinition({ definition, typeName }) {
34 | const { fields, comment } = definition;
35 | // TODO: need to set up for either input type or object type
36 | const fieldsFunction = () => Object.keys(fields)
37 | .reduce((result, fieldName) => {
38 | const { rule, type, comment } = fields[fieldName];
39 | const gqlType = types_1.GRPC_GQL_TYPE_MAPPING[type] || types_1.typeDefinitionCache[type];
40 | // eslint-disable-next-line no-param-reassign
41 | result[fieldName] = {
42 | type: rule === 'repeated' ? graphql_1.GraphQLList(gqlType) : gqlType,
43 | description: comment,
44 | };
45 | return result;
46 | }, {});
47 | const typeDef = {
48 | name: typeName,
49 | fields: fieldsFunction,
50 | description: comment,
51 | };
52 | // CONVENTION - types that end with `Input` are GraphQL input types
53 | const type = typeName.endsWith('Input')
54 | ? new graphql_1.GraphQLInputObjectType(typeDef)
55 | : new graphql_1.GraphQLObjectType(typeDef);
56 | types_1.typeDefinitionCache[typeName] = type;
57 | return type;
58 | }
59 | exports.getGraphqlTypeFromProtoDefinition = getGraphqlTypeFromProtoDefinition;
60 | //# sourceMappingURL=type_converter.js.map
--------------------------------------------------------------------------------
/lib/type_converter.js.map:
--------------------------------------------------------------------------------
1 | {"version":3,"file":"type_converter.js","sourceRoot":"","sources":["../src/type_converter.ts"],"names":[],"mappings":";;AACA,6BAA6B;AAC7B,qCAMiB;AAEjB,mCAGiB;AAgBjB,SAAS,oBAAoB,CAAC,KAAU;IACtC,IAAI,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE;QACtB,cAAc;QACd,OAAO,KAAK,CAAC,QAAQ,EAAE,CAAC;KACzB;IAED,OAAO,KAAK,CAAC;AACf,CAAC;AAED,4CAA4C;AAC5C,SAAgB,4BAA4B,CAAC,OAAO,EAAE,OAAO;IAC3D,MAAM,MAAM,GAAG,OAAO,CAAC,SAAS,EAAE,CAAC;IAEnC,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,OAAO,CAAC,CAAC,GAAG,EAAE,EAAE;QAClC,MAAM,KAAK,GAAG,OAAO,CAAC,GAAG,CAAC,CAAC;QAC3B,MAAM,KAAK,GAAG,MAAM,CAAC,GAAG,CAAC,CAAC;QAC1B,MAAM,SAAS,GAAG,KAAK,CAAC,IAAI,CAAC;QAE7B,IAAI,oBAAU,CAAC,SAAS,CAAC,EAAE;YACzB,eAAe;YACf,6CAA6C;YAC7C,OAAO,CAAC,GAAG,CAAC,GAAG,KAAK,CAAC,GAAG,CAAC,oBAAoB,CAAC,CAAC;SAChD;aAAM;YACL,6CAA6C;YAC7C,OAAO,CAAC,GAAG,CAAC,GAAG,oBAAoB,CAAC,KAAK,CAAC,CAAC;SAC5C;IACH,CAAC,CAAC,CAAC;IAEH,OAAO,OAAO,CAAC;AACjB,CAAC;AAnBD,oEAmBC;AAED,SAAgB,iCAAiC,CAC/C,EAAE,UAAU,EAAE,QAAQ,EAAwB;IAE9C,MAAM,EAAE,MAAM,EAAE,OAAO,EAAE,GAAG,UAAU,CAAC;IAEvC,4DAA4D;IAC5D,MAAM,cAAc,GAAG,GAAG,EAAE,CAAC,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC;SAC7C,MAAM,CACL,CAAC,MAAM,EAAE,SAAS,EAAE,EAAE;QACpB,MAAM,EAAE,IAAI,EAAE,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,SAAS,CAAC,CAAC;QAElD,MAAM,OAAO,GAAG,6BAAqB,CAAC,IAAI,CAAC,IAAI,2BAAmB,CAAC,IAAI,CAAC,CAAC;QAEzE,6CAA6C;QAC7C,MAAM,CAAC,SAAS,CAAC,GAAG;YAClB,IAAI,EAAE,IAAI,KAAK,UAAU,CAAC,CAAC,CAAC,qBAAW,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,OAAO;YAC1D,WAAW,EAAE,OAAO;SACrB,CAAC;QAEF,OAAO,MAAM,CAAC;IAChB,CAAC,EACD,EAAE,CACH,CAAC;IAEJ,MAAM,OAAO,GAAG;QACd,IAAI,EAAE,QAAQ;QACd,MAAM,EAAE,cAAc;QACtB,WAAW,EAAE,OAAO;KACrB,CAAC;IAEF,mEAAmE;IACnE,MAAM,IAAI,GAAG,QAAQ,CAAC,QAAQ,CAAC,OAAO,CAAC;QACrC,CAAC,CAAC,IAAI,gCAAsB,CAAC,OAAO,CAAC;QACrC,CAAC,CAAC,IAAI,2BAAiB,CAAC,OAAO,CAAC,CAAC;IAEnC,2BAAmB,CAAC,QAAQ,CAAC,GAAG,IAAI,CAAC;IACrC,OAAO,IAAI,CAAC;AACd,CAAC;AArCD,8EAqCC"}
--------------------------------------------------------------------------------
/lib/types.d.ts:
--------------------------------------------------------------------------------
1 | import { GraphQLType } from 'graphql';
2 | export interface GrpcGraphqlSchemaConfiguration {
3 | endpoint: string;
4 | protoFilePath: string;
5 | serviceName: string;
6 | packageName: string;
7 | }
8 | export interface TypeMapping {
9 | [key: string]: GraphQLType;
10 | }
11 | export declare const GRPC_GQL_TYPE_MAPPING: TypeMapping;
12 | export declare const typeDefinitionCache: TypeMapping;
13 |
--------------------------------------------------------------------------------
/lib/types.js:
--------------------------------------------------------------------------------
1 | "use strict";
2 | Object.defineProperty(exports, "__esModule", { value: true });
3 | const graphql_1 = require("graphql");
4 | // https://developers.google.com/protocol-buffers/docs/proto3#scalar
5 | // https://www.apollographql.com/docs/apollo-server/schemas/types.html
6 | exports.GRPC_GQL_TYPE_MAPPING = {
7 | int32: graphql_1.GraphQLInt,
8 | int64: graphql_1.GraphQLFloat,
9 | float: graphql_1.GraphQLFloat,
10 | double: graphql_1.GraphQLFloat,
11 | string: graphql_1.GraphQLString,
12 | bool: graphql_1.GraphQLBoolean,
13 | };
14 | exports.typeDefinitionCache = {
15 | ServerStatus: new graphql_1.GraphQLObjectType({
16 | name: 'ServerStatus',
17 | description: 'status of the server',
18 | fields: () => ({
19 | status: {
20 | type: graphql_1.GraphQLString,
21 | descripton: 'status string',
22 | },
23 | }),
24 | }),
25 | };
26 | //# sourceMappingURL=types.js.map
--------------------------------------------------------------------------------
/lib/types.js.map:
--------------------------------------------------------------------------------
1 | {"version":3,"file":"types.js","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":";;AAAA,qCAOiB;AAajB,oEAAoE;AACpE,sEAAsE;AACzD,QAAA,qBAAqB,GAAgB;IAChD,KAAK,EAAE,oBAAU;IACjB,KAAK,EAAE,sBAAY;IACnB,KAAK,EAAE,sBAAY;IACnB,MAAM,EAAE,sBAAY;IACpB,MAAM,EAAE,uBAAa;IACrB,IAAI,EAAE,wBAAc;CACrB,CAAC;AAEW,QAAA,mBAAmB,GAAgB;IAC9C,YAAY,EAAE,IAAI,2BAAiB,CAAC;QAClC,IAAI,EAAE,cAAc;QACpB,WAAW,EAAE,sBAAsB;QACnC,MAAM,EAAE,GAAG,EAAE,CAAC,CAAC;YACb,MAAM,EAAE;gBACN,IAAI,EAAE,uBAAa;gBACnB,UAAU,EAAE,eAAe;aAC5B;SACF,CAAC;KACH,CAAC;CACH,CAAC"}
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "grpc-graphql-schema",
3 | "version": "0.0.9",
4 | "description": "Convert gRPC proto Definition into GraphQL Schema",
5 | "main": "lib/index.js",
6 | "repository": "https://github.com/xanthous-tech/grpc-graphql-schema",
7 | "author": "Simon Liang ",
8 | "license": "MIT",
9 | "private": false,
10 | "scripts": {
11 | "build": "tsc --project .",
12 | "start": "node ."
13 | },
14 | "devDependencies": {
15 | "@types/graphql": "^14.0.4",
16 | "@types/node": "^10.12.18",
17 | "tslint": "^5.12.1",
18 | "tslint-config-airbnb": "^5.11.1",
19 | "typescript": "^3.2.2"
20 | },
21 | "peerDependencies": {
22 | "graphql": "^14.0.2"
23 | },
24 | "dependencies": {
25 | "graphql": "^14.0.2",
26 | "grpc": "^1.17.0",
27 | "grpc-caller": "^0.11.0",
28 | "lodash": "^4.17.11",
29 | "long": "^4.0.0",
30 | "protobufjs": "^6.8.8"
31 | }
32 | }
33 |
--------------------------------------------------------------------------------
/src/index.ts:
--------------------------------------------------------------------------------
1 | import * as protobuf from 'protobufjs';
2 | import * as _ from 'lodash';
3 | import * as grpcCaller from 'grpc-caller';
4 | import {
5 | GraphQLSchema,
6 | GraphQLInputObjectType,
7 | GraphQLObjectType,
8 | } from 'graphql';
9 |
10 | import { GrpcGraphqlSchemaConfiguration } from './types';
11 | import { getGraphqlTypeFromProtoDefinition } from './type_converter';
12 | import {
13 | getGraphqlQueriesFromProtoService,
14 | getGraphQlSubscriptionsFromProtoService,
15 | getGraphqlMutationsFromProtoService,
16 | } from './service_converter';
17 | import { getPackageProtoDefinition } from './protobuf';
18 |
19 | export {
20 | getGraphqlQueriesFromProtoService,
21 | getGraphqlMutationsFromProtoService,
22 | getGraphQlSubscriptionsFromProtoService,
23 | } from './service_converter';
24 |
25 | export {
26 | convertGrpcTypeToGraphqlType,
27 | getGraphqlTypeFromProtoDefinition,
28 | } from './type_converter';
29 | export {
30 | GRPC_GQL_TYPE_MAPPING,
31 | GrpcGraphqlSchemaConfiguration,
32 | typeDefinitionCache,
33 | } from './types';
34 |
35 | type GraphqlInputTypes = GraphQLInputObjectType | GraphQLObjectType;
36 |
37 | export async function getGraphqlSchemaFromGrpc({
38 | endpoint,
39 | protoFilePath,
40 | serviceName,
41 | packageName,
42 | }: GrpcGraphqlSchemaConfiguration): Promise {
43 | const client = grpcCaller(
44 | endpoint,
45 | protoFilePath,
46 | serviceName,
47 | null,
48 | {
49 | 'grpc.max_send_message_length': -1,
50 | 'grpc.max_receive_message_length': -1,
51 | },
52 | );
53 |
54 | const { nested }: protobuf.INamespace =
55 | await getPackageProtoDefinition(protoFilePath, packageName);
56 |
57 | const types: GraphqlInputTypes[] = Object.keys(nested)
58 | .filter((key: string) => 'fields' in nested[key])
59 | .reduce(
60 | (acc: GraphqlInputTypes[], key: string) => {
61 | const definition: protobuf.AnyNestedObject = nested[key];
62 |
63 | // skip empty
64 | if (key.startsWith('Empty')) {
65 | return acc;
66 | }
67 |
68 | if ((definition).fields) {
69 | return acc.concat([
70 | getGraphqlTypeFromProtoDefinition({
71 | definition: (definition),
72 | typeName: key,
73 | }),
74 | ]);
75 | }
76 |
77 | return acc;
78 | },
79 | [],
80 | );
81 |
82 | const query = Object.keys(nested)
83 | .filter((key: string) => 'methods' in nested[key] && key === serviceName)
84 | .reduce(
85 | (__: any, key: string): GraphQLObjectType | null => {
86 | const definition = nested[key];
87 |
88 | return getGraphqlQueriesFromProtoService({
89 | client,
90 | definition,
91 | serviceName: key,
92 | });
93 | },
94 | null,
95 | );
96 |
97 | const mutation = Object.keys(nested)
98 | .filter((key: string) => 'methods' in nested[key] && key === serviceName)
99 | .reduce(
100 | (__: any, key: string): GraphQLObjectType | null => {
101 | const definition = nested[key];
102 |
103 | return getGraphqlMutationsFromProtoService({
104 | client,
105 | definition,
106 | serviceName: key,
107 | });
108 | },
109 | null,
110 | );
111 |
112 | const subscription = Object.keys(nested)
113 | .filter(key => 'methods' in nested[key] && key === serviceName)
114 | .reduce(
115 | (__: any, key: string): GraphQLObjectType | null => {
116 | const definition = nested[key];
117 |
118 | return getGraphQlSubscriptionsFromProtoService({
119 | client,
120 | definition,
121 | serviceName: key,
122 | });
123 | },
124 | null,
125 | );
126 |
127 | return new GraphQLSchema({
128 | types,
129 | query,
130 | mutation,
131 | subscription,
132 | });
133 | }
134 |
--------------------------------------------------------------------------------
/src/protobuf.ts:
--------------------------------------------------------------------------------
1 | import * as _ from 'lodash';
2 | import * as protobuf from 'protobufjs';
3 |
4 | export async function getPackageProtoDefinition(
5 | protoFile: string,
6 | packageName: string,
7 | ): Promise {
8 | const protoDefinition = await protobuf.load(protoFile);
9 | const protoDefinitionObject = await protoDefinition.toJSON({
10 | keepComments: true,
11 | });
12 | const packagePaths: string[] = packageName.split('.');
13 |
14 | for (let i: number = 0; i < packagePaths.length; i += 2) {
15 | packagePaths.splice(i, 0, 'nested');
16 | }
17 |
18 | return _.get(protoDefinitionObject, packagePaths.join('.'));
19 | }
20 |
--------------------------------------------------------------------------------
/src/service_converter.ts:
--------------------------------------------------------------------------------
1 | import * as _ from 'lodash';
2 |
3 | import {
4 | GraphQLObjectType, GraphQLFieldConfigMap, Thunk, GraphQLFieldConfig, GraphQLOutputType,
5 | } from 'graphql';
6 |
7 | import { withAsyncIteratorCancel } from './subscription';
8 |
9 | import {
10 | convertGrpcTypeToGraphqlType,
11 | } from './type_converter';
12 |
13 | import {
14 | typeDefinitionCache,
15 | } from './types';
16 |
17 | function getGraphqlMethodsFromProtoService({
18 | definition,
19 | serviceName,
20 | client,
21 | methodType,
22 | }) {
23 | const { methods } = definition;
24 | const fields: Thunk> = () => Object.keys(methods).reduce(
25 | (result: GraphQLFieldConfigMap, methodName): GraphQLFieldConfigMap => {
26 | const args = {};
27 | const {
28 | requestType: requestArgName,
29 | responseType,
30 | responseStream,
31 | comment,
32 | } = methods[methodName];
33 |
34 | if (responseStream) {
35 | // responseStream should be in subscriptions
36 | return result;
37 | }
38 |
39 | // filter for mutations
40 | if (methodType === 'Mutation' && !methodName.startsWith('Set')) {
41 | return result;
42 | }
43 |
44 | // filter out ping for mutation
45 | if (methodType === 'Mutation' && methodName === 'ping') {
46 | return result;
47 | }
48 |
49 | if (!requestArgName.startsWith('Empty')) {
50 | args[requestArgName] = {
51 | type: typeDefinitionCache[requestArgName],
52 | };
53 | }
54 |
55 | const queryField = {
56 | args,
57 | type: typeDefinitionCache[responseType],
58 | description: comment,
59 | resolve: async (__, arg) => {
60 | const response = await client[methodName](
61 | arg[requestArgName] || {},
62 | {},
63 | {
64 | deadline:
65 | Date.now() + (Number(process.env.REQUEST_TIMEOUT) || 200000),
66 | },
67 | );
68 | // FIXME: there is a bug in the graphQL type conversion
69 | return response;
70 | // return convertGrpcTypeToGraphqlType(
71 | // response,
72 | // typeDefinitionCache[responseType],
73 | // );
74 | },
75 | };
76 |
77 | // eslint-disable-next-line no-param-reassign
78 | result[`${serviceName}${methodName}`] = >queryField;
79 |
80 | return result;
81 | },
82 | (methodType === 'Mutation') ? {} : {
83 | // adding a default ping
84 | ping: {
85 | type: typeDefinitionCache.ServerStatus,
86 | description: 'query for getting server status',
87 | resolve: () => ({ status: 'online' }),
88 | },
89 | },
90 | );
91 |
92 | if (_.isEmpty(fields())) {
93 | return null;
94 | }
95 |
96 | return new GraphQLObjectType({
97 | fields,
98 | name: methodType,
99 | });
100 | }
101 |
102 | export function getGraphqlQueriesFromProtoService({
103 | definition,
104 | serviceName,
105 | client,
106 | }) {
107 | return getGraphqlMethodsFromProtoService({
108 | definition,
109 | serviceName,
110 | client,
111 | methodType: 'Query',
112 | });
113 | }
114 |
115 | export function getGraphqlMutationsFromProtoService({
116 | definition,
117 | serviceName,
118 | client,
119 | }) {
120 | return getGraphqlMethodsFromProtoService({
121 | definition,
122 | serviceName,
123 | client,
124 | methodType: 'Mutation',
125 | });
126 | }
127 |
128 | export function getGraphQlSubscriptionsFromProtoService({
129 | definition,
130 | serviceName,
131 | client,
132 | }) {
133 | const { methods } = definition;
134 | const fields = () => Object.keys(methods).reduce(
135 | (result, methodName) => {
136 | const args = {};
137 | const {
138 | requestType: requestArgName,
139 | responseType,
140 | responseStream,
141 | comment,
142 | } = methods[methodName];
143 |
144 | if (!responseStream) {
145 | // non-responseStream should be in queries / mutations
146 | return result;
147 | }
148 |
149 | if (!requestArgName.startsWith('Empty')) {
150 | args[requestArgName] = {
151 | type: typeDefinitionCache[requestArgName],
152 | };
153 | }
154 |
155 | const subscribeField = {
156 | args,
157 | type: typeDefinitionCache[responseType],
158 | description: comment,
159 | subscribe: async (__, arg, { pubsub }) => {
160 | const response = await client[methodName](
161 | arg[requestArgName] || {},
162 | {},
163 | );
164 |
165 | response.on('data', (data) => {
166 | const payload = {};
167 | payload[`${serviceName}${methodName}`] = convertGrpcTypeToGraphqlType(
168 | data,
169 | typeDefinitionCache[responseType],
170 | );
171 | pubsub.publish(`${methodName}-onSubscribe`, payload);
172 | });
173 |
174 | response.on('error', (error) => {
175 | if (error.code === 1) {
176 | // cancelled
177 | response.removeAllListeners('error');
178 | response.removeAllListeners();
179 | }
180 | });
181 |
182 | response.on('end', () => {
183 | response.removeAllListeners();
184 | });
185 |
186 | const asyncIterator = pubsub.asyncIterator(
187 | `${methodName}-onSubscribe`,
188 | );
189 |
190 | return withAsyncIteratorCancel(asyncIterator, () => {
191 | response.cancel();
192 | });
193 | },
194 | };
195 |
196 | // eslint-disable-next-line no-param-reassign
197 | result[`${serviceName}${methodName}`] = subscribeField;
198 |
199 | return result;
200 | },
201 | {},
202 | );
203 |
204 | if (_.isEmpty(fields())) {
205 | return null;
206 | }
207 |
208 | return new GraphQLObjectType({
209 | fields,
210 | name: 'Subscription',
211 | });
212 | }
213 |
--------------------------------------------------------------------------------
/src/subscription.ts:
--------------------------------------------------------------------------------
1 | // https://github.com/apollographql/graphql-subscriptions/issues/99#issuecomment-400500956
2 | export function withAsyncIteratorCancel(asyncIterator, onCancel) {
3 | return {
4 | ...asyncIterator,
5 | return() {
6 | if (typeof onCancel === 'function') {
7 | onCancel();
8 | }
9 | return asyncIterator.return
10 | ? asyncIterator.return()
11 | : Promise.resolve({ value: undefined, done: true });
12 | },
13 | };
14 | }
--------------------------------------------------------------------------------
/src/type_converter.ts:
--------------------------------------------------------------------------------
1 | import * as protobuf from 'protobufjs';
2 | import * as Long from 'long';
3 | import {
4 | GraphQLList,
5 | GraphQLInputObjectType,
6 | GraphQLObjectType,
7 | isListType,
8 | Thunk,
9 | } from 'graphql';
10 |
11 | import {
12 | GRPC_GQL_TYPE_MAPPING,
13 | typeDefinitionCache,
14 | } from './types';
15 |
16 | interface IFieldWithComment extends protobuf.IField {
17 | comment?: string | null | undefined;
18 | }
19 |
20 | interface ITypeWithComment extends protobuf.IType {
21 | fields: { [k: string]: IFieldWithComment };
22 | comment?: string | null | undefined;
23 | }
24 |
25 | interface ProtoDefinitionInput {
26 | definition: ITypeWithComment;
27 | typeName: string;
28 | }
29 |
30 | function convertToGraphqlType(value: any): any {
31 | if (Long.isLong(value)) {
32 | // conver long
33 | return value.toNumber();
34 | }
35 |
36 | return value;
37 | }
38 |
39 | // TODO: this convert method is not complete
40 | export function convertGrpcTypeToGraphqlType(payload, typeDef) {
41 | const fields = typeDef.getFields();
42 |
43 | Object.keys(fields).forEach((key) => {
44 | const value = payload[key];
45 | const field = fields[key];
46 | const fieldType = field.type;
47 |
48 | if (isListType(fieldType)) {
49 | // process list
50 | // eslint-disable-next-line no-param-reassign
51 | payload[key] = value.map(convertToGraphqlType);
52 | } else {
53 | // eslint-disable-next-line no-param-reassign
54 | payload[key] = convertToGraphqlType(value);
55 | }
56 | });
57 |
58 | return payload;
59 | }
60 |
61 | export function getGraphqlTypeFromProtoDefinition(
62 | { definition, typeName }: ProtoDefinitionInput,
63 | ): GraphQLInputObjectType | GraphQLObjectType {
64 | const { fields, comment } = definition;
65 |
66 | // TODO: need to set up for either input type or object type
67 | const fieldsFunction = () => Object.keys(fields)
68 | .reduce(
69 | (result, fieldName) => {
70 | const { rule, type, comment } = fields[fieldName];
71 |
72 | const gqlType = GRPC_GQL_TYPE_MAPPING[type] || typeDefinitionCache[type];
73 |
74 | // eslint-disable-next-line no-param-reassign
75 | result[fieldName] = {
76 | type: rule === 'repeated' ? GraphQLList(gqlType) : gqlType,
77 | description: comment,
78 | };
79 |
80 | return result;
81 | },
82 | {},
83 | );
84 |
85 | const typeDef = {
86 | name: typeName,
87 | fields: fieldsFunction,
88 | description: comment,
89 | };
90 |
91 | // CONVENTION - types that end with `Input` are GraphQL input types
92 | const type = typeName.endsWith('Input')
93 | ? new GraphQLInputObjectType(typeDef)
94 | : new GraphQLObjectType(typeDef);
95 |
96 | typeDefinitionCache[typeName] = type;
97 | return type;
98 | }
99 |
--------------------------------------------------------------------------------
/src/types.ts:
--------------------------------------------------------------------------------
1 | import {
2 | GraphQLType,
3 | GraphQLObjectType,
4 | GraphQLInt,
5 | GraphQLFloat,
6 | GraphQLString,
7 | GraphQLBoolean,
8 | } from 'graphql';
9 |
10 | export interface GrpcGraphqlSchemaConfiguration {
11 | endpoint: string;
12 | protoFilePath: string;
13 | serviceName: string;
14 | packageName: string;
15 | }
16 |
17 | export interface TypeMapping {
18 | [key: string]: GraphQLType;
19 | }
20 |
21 | // https://developers.google.com/protocol-buffers/docs/proto3#scalar
22 | // https://www.apollographql.com/docs/apollo-server/schemas/types.html
23 | export const GRPC_GQL_TYPE_MAPPING: TypeMapping = {
24 | int32: GraphQLInt,
25 | int64: GraphQLFloat, // TODO: https://github.com/graphql/graphql-js/issues/292
26 | float: GraphQLFloat,
27 | double: GraphQLFloat,
28 | string: GraphQLString,
29 | bool: GraphQLBoolean,
30 | };
31 |
32 | export const typeDefinitionCache: TypeMapping = {
33 | ServerStatus: new GraphQLObjectType({
34 | name: 'ServerStatus',
35 | description: 'status of the server',
36 | fields: () => ({
37 | status: {
38 | type: GraphQLString,
39 | descripton: 'status string',
40 | },
41 | }),
42 | }),
43 | };
44 |
--------------------------------------------------------------------------------
/src/typings.d.ts:
--------------------------------------------------------------------------------
1 | declare module 'grpc-caller';
2 |
--------------------------------------------------------------------------------
/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "compileOnSave": true,
3 | "compilerOptions": {
4 | "types": [
5 | "node"
6 | ],
7 | "lib": [
8 | "es2015",
9 | "esnext.asynciterable"
10 | ],
11 | "target": "es6",
12 | "module": "commonjs",
13 | "sourceMap": true,
14 | "declaration": true,
15 | "outDir": "lib"
16 | },
17 | "include": [
18 | "src/**/*"
19 | ],
20 | "exclude": [
21 | "node_modules"
22 | ]
23 | }
--------------------------------------------------------------------------------
/tslint.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "tslint-config-airbnb"
3 | }
--------------------------------------------------------------------------------
/yarn.lock:
--------------------------------------------------------------------------------
1 | # THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY.
2 | # yarn lockfile v1
3 |
4 |
5 | "@fimbul/bifrost@^0.17.0":
6 | version "0.17.0"
7 | resolved "https://registry.yarnpkg.com/@fimbul/bifrost/-/bifrost-0.17.0.tgz#f0383ba7e40992e3193dc87e2ddfde2ad62a9cf4"
8 | integrity sha512-gVTkJAOef5HtN6LPmrtt5fAUmBywwlgmObsU3FBhPoNeXPLaIl2zywXkJEtvvVLQnaFmtff3x+wIj5lHRCDE3Q==
9 | dependencies:
10 | "@fimbul/ymir" "^0.17.0"
11 | get-caller-file "^2.0.0"
12 | tslib "^1.8.1"
13 | tsutils "^3.5.0"
14 |
15 | "@fimbul/ymir@^0.17.0":
16 | version "0.17.0"
17 | resolved "https://registry.yarnpkg.com/@fimbul/ymir/-/ymir-0.17.0.tgz#4f28389b9f804d1cd202e11983af1743488b7815"
18 | integrity sha512-xMXM9KTXRLHLVS6dnX1JhHNEkmWHcAVCQ/4+DA1KKwC/AFnGHzu/7QfQttEPgw3xplT+ILf9e3i64jrFwB3JtA==
19 | dependencies:
20 | inversify "^5.0.0"
21 | reflect-metadata "^0.1.12"
22 | tslib "^1.8.1"
23 |
24 | "@grpc/proto-loader@^0.3.0":
25 | version "0.3.0"
26 | resolved "https://registry.yarnpkg.com/@grpc/proto-loader/-/proto-loader-0.3.0.tgz#c127d3859bff895f220453612ba04b923af0c584"
27 | integrity sha512-9b8S/V+3W4Gv7G/JKSZ48zApgyYbfIR7mAC9XNnaSWme3zj57MIESu0ELzm9j5oxNIpFG8DgO00iJMIUZ5luqw==
28 | dependencies:
29 | "@types/lodash" "^4.14.104"
30 | "@types/node" "^9.4.6"
31 | lodash "^4.17.5"
32 | protobufjs "^6.8.6"
33 |
34 | "@protobufjs/aspromise@^1.1.1", "@protobufjs/aspromise@^1.1.2":
35 | version "1.1.2"
36 | resolved "https://registry.yarnpkg.com/@protobufjs/aspromise/-/aspromise-1.1.2.tgz#9b8b0cc663d669a7d8f6f5d0893a14d348f30fbf"
37 | integrity sha1-m4sMxmPWaafY9vXQiToU00jzD78=
38 |
39 | "@protobufjs/base64@^1.1.2":
40 | version "1.1.2"
41 | resolved "https://registry.yarnpkg.com/@protobufjs/base64/-/base64-1.1.2.tgz#4c85730e59b9a1f1f349047dbf24296034bb2735"
42 | integrity sha512-AZkcAA5vnN/v4PDqKyMR5lx7hZttPDgClv83E//FMNhR2TMcLUhfRUBHCmSl0oi9zMgDDqRUJkSxO3wm85+XLg==
43 |
44 | "@protobufjs/codegen@^2.0.4":
45 | version "2.0.4"
46 | resolved "https://registry.yarnpkg.com/@protobufjs/codegen/-/codegen-2.0.4.tgz#7ef37f0d010fb028ad1ad59722e506d9262815cb"
47 | integrity sha512-YyFaikqM5sH0ziFZCN3xDC7zeGaB/d0IUb9CATugHWbd1FRFwWwt4ld4OYMPWu5a3Xe01mGAULCdqhMlPl29Jg==
48 |
49 | "@protobufjs/eventemitter@^1.1.0":
50 | version "1.1.0"
51 | resolved "https://registry.yarnpkg.com/@protobufjs/eventemitter/-/eventemitter-1.1.0.tgz#355cbc98bafad5978f9ed095f397621f1d066b70"
52 | integrity sha1-NVy8mLr61ZePntCV85diHx0Ga3A=
53 |
54 | "@protobufjs/fetch@^1.1.0":
55 | version "1.1.0"
56 | resolved "https://registry.yarnpkg.com/@protobufjs/fetch/-/fetch-1.1.0.tgz#ba99fb598614af65700c1619ff06d454b0d84c45"
57 | integrity sha1-upn7WYYUr2VwDBYZ/wbUVLDYTEU=
58 | dependencies:
59 | "@protobufjs/aspromise" "^1.1.1"
60 | "@protobufjs/inquire" "^1.1.0"
61 |
62 | "@protobufjs/float@^1.0.2":
63 | version "1.0.2"
64 | resolved "https://registry.yarnpkg.com/@protobufjs/float/-/float-1.0.2.tgz#5e9e1abdcb73fc0a7cb8b291df78c8cbd97b87d1"
65 | integrity sha1-Xp4avctz/Ap8uLKR33jIy9l7h9E=
66 |
67 | "@protobufjs/inquire@^1.1.0":
68 | version "1.1.0"
69 | resolved "https://registry.yarnpkg.com/@protobufjs/inquire/-/inquire-1.1.0.tgz#ff200e3e7cf2429e2dcafc1140828e8cc638f089"
70 | integrity sha1-/yAOPnzyQp4tyvwRQIKOjMY48Ik=
71 |
72 | "@protobufjs/path@^1.1.2":
73 | version "1.1.2"
74 | resolved "https://registry.yarnpkg.com/@protobufjs/path/-/path-1.1.2.tgz#6cc2b20c5c9ad6ad0dccfd21ca7673d8d7fbf68d"
75 | integrity sha1-bMKyDFya1q0NzP0hynZz2Nf79o0=
76 |
77 | "@protobufjs/pool@^1.1.0":
78 | version "1.1.0"
79 | resolved "https://registry.yarnpkg.com/@protobufjs/pool/-/pool-1.1.0.tgz#09fd15f2d6d3abfa9b65bc366506d6ad7846ff54"
80 | integrity sha1-Cf0V8tbTq/qbZbw2ZQbWrXhG/1Q=
81 |
82 | "@protobufjs/utf8@^1.1.0":
83 | version "1.1.0"
84 | resolved "https://registry.yarnpkg.com/@protobufjs/utf8/-/utf8-1.1.0.tgz#a777360b5b39a1a2e5106f8e858f2fd2d060c570"
85 | integrity sha1-p3c2C1s5oaLlEG+OhY8v0tBgxXA=
86 |
87 | "@types/graphql@^14.0.4":
88 | version "14.0.4"
89 | resolved "https://registry.yarnpkg.com/@types/graphql/-/graphql-14.0.4.tgz#d71a75967cd93c33eaea32b626b362ce0f2b2ae9"
90 | integrity sha512-gI98ANelzzpq7lZzuYCUJg8LZDjQc7ekj7cxoWt8RezOKaVaAyK27U6AHa9LEqikP1NUhyi8blQQkHYHVRZ7Tg==
91 |
92 | "@types/lodash@^4.14.104":
93 | version "4.14.119"
94 | resolved "https://registry.yarnpkg.com/@types/lodash/-/lodash-4.14.119.tgz#be847e5f4bc3e35e46d041c394ead8b603ad8b39"
95 | integrity sha512-Z3TNyBL8Vd/M9D9Ms2S3LmFq2sSMzahodD6rCS9V2N44HUMINb75jNkSuwAx7eo2ufqTdfOdtGQpNbieUjPQmw==
96 |
97 | "@types/long@^4.0.0":
98 | version "4.0.0"
99 | resolved "https://registry.yarnpkg.com/@types/long/-/long-4.0.0.tgz#719551d2352d301ac8b81db732acb6bdc28dbdef"
100 | integrity sha512-1w52Nyx4Gq47uuu0EVcsHBxZFJgurQ+rTKS3qMHxR1GY2T8c2AJYd6vZoZ9q1rupaDjU0yT+Jc2XTyXkjeMA+Q==
101 |
102 | "@types/node@^10.1.0", "@types/node@^10.12.18":
103 | version "10.12.18"
104 | resolved "https://registry.yarnpkg.com/@types/node/-/node-10.12.18.tgz#1d3ca764718915584fcd9f6344621b7672665c67"
105 | integrity sha512-fh+pAqt4xRzPfqA6eh3Z2y6fyZavRIumvjhaCL753+TVkGKGhpPeyrJG2JftD0T9q4GF00KjefsQ+PQNDdWQaQ==
106 |
107 | "@types/node@^9.4.6":
108 | version "9.6.41"
109 | resolved "https://registry.yarnpkg.com/@types/node/-/node-9.6.41.tgz#e57c3152eb2e7ec748c733cebd0c095b437c5d37"
110 | integrity sha512-sPZWEbFMz6qAy9SLY7jh5cgepmsiwqUUHjvEm8lpU6kug2hmmcyuTnwhoGw/GWpI5Npue4EqvsiQQI0eWjW/ZA==
111 |
112 | abbrev@1:
113 | version "1.1.1"
114 | resolved "https://registry.yarnpkg.com/abbrev/-/abbrev-1.1.1.tgz#f8f2c887ad10bf67f634f005b6987fed3179aac8"
115 | integrity sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==
116 |
117 | ansi-regex@^2.0.0:
118 | version "2.1.1"
119 | resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-2.1.1.tgz#c3b33ab5ee360d86e0e628f0468ae7ef27d654df"
120 | integrity sha1-w7M6te42DYbg5ijwRorn7yfWVN8=
121 |
122 | ansi-regex@^3.0.0:
123 | version "3.0.0"
124 | resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-3.0.0.tgz#ed0317c322064f79466c02966bddb605ab37d998"
125 | integrity sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=
126 |
127 | ansi-styles@^2.2.1:
128 | version "2.2.1"
129 | resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-2.2.1.tgz#b432dd3358b634cf75e1e4664368240533c1ddbe"
130 | integrity sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=
131 |
132 | ansi-styles@^3.2.1:
133 | version "3.2.1"
134 | resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-3.2.1.tgz#41fbb20243e50b12be0f04b8dedbf07520ce841d"
135 | integrity sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==
136 | dependencies:
137 | color-convert "^1.9.0"
138 |
139 | aproba@^1.0.3:
140 | version "1.2.0"
141 | resolved "https://registry.yarnpkg.com/aproba/-/aproba-1.2.0.tgz#6802e6264efd18c790a1b0d517f0f2627bf2c94a"
142 | integrity sha512-Y9J6ZjXtoYh8RnXVCMOU/ttDmk1aBjunq9vO0ta5x85WDQiQfUF9sIPBITdbiiIVcBo03Hi3jMxigBtsddlXRw==
143 |
144 | are-we-there-yet@~1.1.2:
145 | version "1.1.5"
146 | resolved "https://registry.yarnpkg.com/are-we-there-yet/-/are-we-there-yet-1.1.5.tgz#4b35c2944f062a8bfcda66410760350fe9ddfc21"
147 | integrity sha512-5hYdAkZlcG8tOLujVDTgCT+uPX0VnpAH28gWsLfzpXYm7wP6mp5Q/gYyR7YQ0cKVJcXJnl3j2kpBan13PtQf6w==
148 | dependencies:
149 | delegates "^1.0.0"
150 | readable-stream "^2.0.6"
151 |
152 | argparse@^1.0.7:
153 | version "1.0.10"
154 | resolved "https://registry.yarnpkg.com/argparse/-/argparse-1.0.10.tgz#bcd6791ea5ae09725e17e5ad988134cd40b3d911"
155 | integrity sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==
156 | dependencies:
157 | sprintf-js "~1.0.2"
158 |
159 | ascli@~1:
160 | version "1.0.1"
161 | resolved "https://registry.yarnpkg.com/ascli/-/ascli-1.0.1.tgz#bcfa5974a62f18e81cabaeb49732ab4a88f906bc"
162 | integrity sha1-vPpZdKYvGOgcq660lzKrSoj5Brw=
163 | dependencies:
164 | colour "~0.7.1"
165 | optjs "~3.2.2"
166 |
167 | async@^2.6.1:
168 | version "2.6.1"
169 | resolved "https://registry.yarnpkg.com/async/-/async-2.6.1.tgz#b245a23ca71930044ec53fa46aa00a3e87c6a610"
170 | integrity sha512-fNEiL2+AZt6AlAw/29Cr0UDe4sRAHCpEHh54WMz+Bb7QfNcFw4h3loofyJpLeQs4Yx7yuqu/2dLgM5hKOs6HlQ==
171 | dependencies:
172 | lodash "^4.17.10"
173 |
174 | babel-code-frame@^6.22.0:
175 | version "6.26.0"
176 | resolved "https://registry.yarnpkg.com/babel-code-frame/-/babel-code-frame-6.26.0.tgz#63fd43f7dc1e3bb7ce35947db8fe369a3f58c74b"
177 | integrity sha1-Y/1D99weO7fONZR9uP42mj9Yx0s=
178 | dependencies:
179 | chalk "^1.1.3"
180 | esutils "^2.0.2"
181 | js-tokens "^3.0.2"
182 |
183 | balanced-match@^1.0.0:
184 | version "1.0.0"
185 | resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-1.0.0.tgz#89b4d199ab2bee49de164ea02b89ce462d71b767"
186 | integrity sha1-ibTRmasr7kneFk6gK4nORi1xt2c=
187 |
188 | brace-expansion@^1.1.7:
189 | version "1.1.11"
190 | resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.11.tgz#3c7fcbf529d87226f3d2f52b966ff5271eb441dd"
191 | integrity sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==
192 | dependencies:
193 | balanced-match "^1.0.0"
194 | concat-map "0.0.1"
195 |
196 | builtin-modules@^1.1.1:
197 | version "1.1.1"
198 | resolved "https://registry.yarnpkg.com/builtin-modules/-/builtin-modules-1.1.1.tgz#270f076c5a72c02f5b65a47df94c5fe3a278892f"
199 | integrity sha1-Jw8HbFpywC9bZaR9+Uxf46J4iS8=
200 |
201 | bytebuffer@~5:
202 | version "5.0.1"
203 | resolved "https://registry.yarnpkg.com/bytebuffer/-/bytebuffer-5.0.1.tgz#582eea4b1a873b6d020a48d58df85f0bba6cfddd"
204 | integrity sha1-WC7qSxqHO20CCkjVjfhfC7ps/d0=
205 | dependencies:
206 | long "~3"
207 |
208 | call-me-maybe@^1.0.1:
209 | version "1.0.1"
210 | resolved "https://registry.yarnpkg.com/call-me-maybe/-/call-me-maybe-1.0.1.tgz#26d208ea89e37b5cbde60250a15f031c16a4d66b"
211 | integrity sha1-JtII6onje1y95gJQoV8DHBak1ms=
212 |
213 | camelcase@^2.0.1:
214 | version "2.1.1"
215 | resolved "https://registry.yarnpkg.com/camelcase/-/camelcase-2.1.1.tgz#7c1d16d679a1bbe59ca02cacecfb011e201f5a1f"
216 | integrity sha1-fB0W1nmhu+WcoCys7PsBHiAfWh8=
217 |
218 | chalk@^1.1.3:
219 | version "1.1.3"
220 | resolved "https://registry.yarnpkg.com/chalk/-/chalk-1.1.3.tgz#a8115c55e4a702fe4d150abd3872822a7e09fc98"
221 | integrity sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=
222 | dependencies:
223 | ansi-styles "^2.2.1"
224 | escape-string-regexp "^1.0.2"
225 | has-ansi "^2.0.0"
226 | strip-ansi "^3.0.0"
227 | supports-color "^2.0.0"
228 |
229 | chalk@^2.3.0:
230 | version "2.4.2"
231 | resolved "https://registry.yarnpkg.com/chalk/-/chalk-2.4.2.tgz#cd42541677a54333cf541a49108c1432b44c9424"
232 | integrity sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==
233 | dependencies:
234 | ansi-styles "^3.2.1"
235 | escape-string-regexp "^1.0.5"
236 | supports-color "^5.3.0"
237 |
238 | chownr@^1.1.1:
239 | version "1.1.1"
240 | resolved "https://registry.yarnpkg.com/chownr/-/chownr-1.1.1.tgz#54726b8b8fff4df053c42187e801fb4412df1494"
241 | integrity sha512-j38EvO5+LHX84jlo6h4UzmOwi0UgW61WRyPtJz4qaadK5eY3BTS5TY/S1Stc3Uk2lIM6TPevAlULiEJwie860g==
242 |
243 | cliui@^3.0.3:
244 | version "3.2.0"
245 | resolved "https://registry.yarnpkg.com/cliui/-/cliui-3.2.0.tgz#120601537a916d29940f934da3b48d585a39213d"
246 | integrity sha1-EgYBU3qRbSmUD5NNo7SNWFo5IT0=
247 | dependencies:
248 | string-width "^1.0.1"
249 | strip-ansi "^3.0.1"
250 | wrap-ansi "^2.0.0"
251 |
252 | code-point-at@^1.0.0:
253 | version "1.1.0"
254 | resolved "https://registry.yarnpkg.com/code-point-at/-/code-point-at-1.1.0.tgz#0d070b4d043a5bea33a2f1a40e2edb3d9a4ccf77"
255 | integrity sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=
256 |
257 | color-convert@^1.9.0:
258 | version "1.9.3"
259 | resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-1.9.3.tgz#bb71850690e1f136567de629d2d5471deda4c1e8"
260 | integrity sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==
261 | dependencies:
262 | color-name "1.1.3"
263 |
264 | color-name@1.1.3:
265 | version "1.1.3"
266 | resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.3.tgz#a7d0558bd89c42f795dd42328f740831ca53bc25"
267 | integrity sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=
268 |
269 | colour@~0.7.1:
270 | version "0.7.1"
271 | resolved "https://registry.yarnpkg.com/colour/-/colour-0.7.1.tgz#9cb169917ec5d12c0736d3e8685746df1cadf778"
272 | integrity sha1-nLFpkX7F0SwHNtPoaFdG3xyt93g=
273 |
274 | commander@^2.12.1:
275 | version "2.19.0"
276 | resolved "https://registry.yarnpkg.com/commander/-/commander-2.19.0.tgz#f6198aa84e5b83c46054b94ddedbfed5ee9ff12a"
277 | integrity sha512-6tvAOO+D6OENvRAh524Dh9jcfKTYDQAqvqezbCW82xj5X0pSrcpxtvRKHLG0yBY6SD7PSDrJaj+0AiOcKVd1Xg==
278 |
279 | concat-map@0.0.1:
280 | version "0.0.1"
281 | resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b"
282 | integrity sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=
283 |
284 | console-control-strings@^1.0.0, console-control-strings@~1.1.0:
285 | version "1.1.0"
286 | resolved "https://registry.yarnpkg.com/console-control-strings/-/console-control-strings-1.1.0.tgz#3d7cf4464db6446ea644bf4b39507f9851008e8e"
287 | integrity sha1-PXz0Rk22RG6mRL9LOVB/mFEAjo4=
288 |
289 | core-util-is@~1.0.0:
290 | version "1.0.2"
291 | resolved "https://registry.yarnpkg.com/core-util-is/-/core-util-is-1.0.2.tgz#b5fd54220aa2bc5ab57aab7140c940754503c1a7"
292 | integrity sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=
293 |
294 | debug@^2.1.2:
295 | version "2.6.9"
296 | resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.9.tgz#5d128515df134ff327e90a4c93f4e077a536341f"
297 | integrity sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==
298 | dependencies:
299 | ms "2.0.0"
300 |
301 | decamelize@^1.1.1:
302 | version "1.2.0"
303 | resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-1.2.0.tgz#f6534d15148269b20352e7bee26f501f9a191290"
304 | integrity sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=
305 |
306 | deep-extend@^0.6.0:
307 | version "0.6.0"
308 | resolved "https://registry.yarnpkg.com/deep-extend/-/deep-extend-0.6.0.tgz#c4fa7c95404a17a9c3e8ca7e1537312b736330ac"
309 | integrity sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==
310 |
311 | delegates@^1.0.0:
312 | version "1.0.0"
313 | resolved "https://registry.yarnpkg.com/delegates/-/delegates-1.0.0.tgz#84c6e159b81904fdca59a0ef44cd870d31250f9a"
314 | integrity sha1-hMbhWbgZBP3KWaDvRM2HDTElD5o=
315 |
316 | detect-libc@^1.0.2:
317 | version "1.0.3"
318 | resolved "https://registry.yarnpkg.com/detect-libc/-/detect-libc-1.0.3.tgz#fa137c4bd698edf55cd5cd02ac559f91a4c4ba9b"
319 | integrity sha1-+hN8S9aY7fVc1c0CrFWfkaTEups=
320 |
321 | diff@^3.2.0:
322 | version "3.5.0"
323 | resolved "https://registry.yarnpkg.com/diff/-/diff-3.5.0.tgz#800c0dd1e0a8bfbc95835c202ad220fe317e5a12"
324 | integrity sha512-A46qtFgd+g7pDZinpnwiRJtxbC1hpgf0uzP3iG89scHk0AUC7A1TGxf5OiiOUv/JMZR8GOt8hL900hV0bOy5xA==
325 |
326 | doctrine@0.7.2:
327 | version "0.7.2"
328 | resolved "https://registry.yarnpkg.com/doctrine/-/doctrine-0.7.2.tgz#7cb860359ba3be90e040b26b729ce4bfa654c523"
329 | integrity sha1-fLhgNZujvpDgQLJrcpzkv6ZUxSM=
330 | dependencies:
331 | esutils "^1.1.6"
332 | isarray "0.0.1"
333 |
334 | escape-string-regexp@^1.0.2, escape-string-regexp@^1.0.5:
335 | version "1.0.5"
336 | resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz#1b61c0562190a8dff6ae3bb2cf0200ca130b86d4"
337 | integrity sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=
338 |
339 | esprima@^4.0.0:
340 | version "4.0.1"
341 | resolved "https://registry.yarnpkg.com/esprima/-/esprima-4.0.1.tgz#13b04cdb3e6c5d19df91ab6987a8695619b0aa71"
342 | integrity sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==
343 |
344 | esutils@^1.1.6:
345 | version "1.1.6"
346 | resolved "https://registry.yarnpkg.com/esutils/-/esutils-1.1.6.tgz#c01ccaa9ae4b897c6d0c3e210ae52f3c7a844375"
347 | integrity sha1-wBzKqa5LiXxtDD4hCuUvPHqEQ3U=
348 |
349 | esutils@^2.0.2:
350 | version "2.0.2"
351 | resolved "https://registry.yarnpkg.com/esutils/-/esutils-2.0.2.tgz#0abf4f1caa5bcb1f7a9d8acc6dea4faaa04bac9b"
352 | integrity sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=
353 |
354 | fs-minipass@^1.2.5:
355 | version "1.2.5"
356 | resolved "https://registry.yarnpkg.com/fs-minipass/-/fs-minipass-1.2.5.tgz#06c277218454ec288df77ada54a03b8702aacb9d"
357 | integrity sha512-JhBl0skXjUPCFH7x6x61gQxrKyXsxB5gcgePLZCwfyCGGsTISMoIeObbrvVeP6Xmyaudw4TT43qV2Gz+iyd2oQ==
358 | dependencies:
359 | minipass "^2.2.1"
360 |
361 | fs.realpath@^1.0.0:
362 | version "1.0.0"
363 | resolved "https://registry.yarnpkg.com/fs.realpath/-/fs.realpath-1.0.0.tgz#1504ad2523158caa40db4a2787cb01411994ea4f"
364 | integrity sha1-FQStJSMVjKpA20onh8sBQRmU6k8=
365 |
366 | gauge@~2.7.3:
367 | version "2.7.4"
368 | resolved "https://registry.yarnpkg.com/gauge/-/gauge-2.7.4.tgz#2c03405c7538c39d7eb37b317022e325fb018bf7"
369 | integrity sha1-LANAXHU4w51+s3sxcCLjJfsBi/c=
370 | dependencies:
371 | aproba "^1.0.3"
372 | console-control-strings "^1.0.0"
373 | has-unicode "^2.0.0"
374 | object-assign "^4.1.0"
375 | signal-exit "^3.0.0"
376 | string-width "^1.0.1"
377 | strip-ansi "^3.0.1"
378 | wide-align "^1.1.0"
379 |
380 | get-caller-file@^2.0.0:
381 | version "2.0.1"
382 | resolved "https://registry.yarnpkg.com/get-caller-file/-/get-caller-file-2.0.1.tgz#25835260d3a2b9665fcdbb08cb039a7bbf7011c0"
383 | integrity sha512-SpOZHfz845AH0wJYVuZk2jWDqFmu7Xubsx+ldIpwzy5pDUpu7OJHK7QYNSA2NPlDSKQwM1GFaAkciOWjjW92Sg==
384 |
385 | glob@^7.0.5, glob@^7.1.1, glob@^7.1.3:
386 | version "7.1.3"
387 | resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.3.tgz#3960832d3f1574108342dafd3a67b332c0969df1"
388 | integrity sha512-vcfuiIxogLV4DlGBHIUOwI0IbrJ8HWPc4MU7HzviGeNho/UJDfi6B5p3sHeWIQ0KGIU0Jpxi5ZHxemQfLkkAwQ==
389 | dependencies:
390 | fs.realpath "^1.0.0"
391 | inflight "^1.0.4"
392 | inherits "2"
393 | minimatch "^3.0.4"
394 | once "^1.3.0"
395 | path-is-absolute "^1.0.0"
396 |
397 | graphql@^14.0.2:
398 | version "14.0.2"
399 | resolved "https://registry.yarnpkg.com/graphql/-/graphql-14.0.2.tgz#7dded337a4c3fd2d075692323384034b357f5650"
400 | integrity sha512-gUC4YYsaiSJT1h40krG3J+USGlwhzNTXSb4IOZljn9ag5Tj+RkoXrWp+Kh7WyE3t1NCfab5kzCuxBIvOMERMXw==
401 | dependencies:
402 | iterall "^1.2.2"
403 |
404 | grpc-caller@^0.11.0:
405 | version "0.11.0"
406 | resolved "https://registry.yarnpkg.com/grpc-caller/-/grpc-caller-0.11.0.tgz#6974c126cdee66d80aeb9a2499f8fe2d91ca966f"
407 | integrity sha512-8/rK6+wHlPRNU2YvQtecQHDAiDr24rW36W9r+XmIpAetoxtqtC3ItOSAXO/xfV1Zt9ZiBTjn6srKvwWwBVrZWw==
408 | dependencies:
409 | "@grpc/proto-loader" "^0.3.0"
410 | async "^2.6.1"
411 | call-me-maybe "^1.0.1"
412 | grpc-create-metadata "^3.0.0"
413 | grpc-inspect "^0.6.0"
414 | lodash "^4.17.11"
415 | promisify-call "^2.0.0"
416 |
417 | grpc-create-metadata@^3.0.0:
418 | version "3.0.0"
419 | resolved "https://registry.yarnpkg.com/grpc-create-metadata/-/grpc-create-metadata-3.0.0.tgz#54ceb3351959454c59a11bf0e5e38975452193d0"
420 | integrity sha512-Gr+wYv4NdlG1fKbk7W60xI+6tgWaereF/8ga1NTo9W7IhCAH+mqMt6NDXYBwa9v4KFLWKWngNhDSdGU+HLVdIw==
421 | dependencies:
422 | lodash.forown "^4.4.0"
423 |
424 | grpc-inspect@^0.6.0:
425 | version "0.6.0"
426 | resolved "https://registry.yarnpkg.com/grpc-inspect/-/grpc-inspect-0.6.0.tgz#c10fbf920ece85f315c249ab569e0a1739e711be"
427 | integrity sha512-pKW9FvIex0oLI18ms8SkEEvuR0UB1YVEFPecIe457XsxvPMM5gJYjMfuSaCeFVJ1Hv3V6vJYUxTHCy/+HgL0Ww==
428 | dependencies:
429 | lodash "^4.17.11"
430 | traverse "^0.6.6"
431 |
432 | grpc@^1.17.0:
433 | version "1.17.0"
434 | resolved "https://registry.yarnpkg.com/grpc/-/grpc-1.17.0.tgz#d7971dd39bd4eec90c69a048f7727795ab504876"
435 | integrity sha512-5zb5ilwHlsiWfE2Abq/IN5SkHQ2zi4QF/u9Gewcw5DO3y+hGTtzZUiMK52MX3YZHAIRjqxDcO3fx0jLhPjT8Zw==
436 | dependencies:
437 | lodash.camelcase "^4.3.0"
438 | lodash.clone "^4.5.0"
439 | nan "^2.0.0"
440 | node-pre-gyp "^0.12.0"
441 | protobufjs "^5.0.3"
442 |
443 | has-ansi@^2.0.0:
444 | version "2.0.0"
445 | resolved "https://registry.yarnpkg.com/has-ansi/-/has-ansi-2.0.0.tgz#34f5049ce1ecdf2b0649af3ef24e45ed35416d91"
446 | integrity sha1-NPUEnOHs3ysGSa8+8k5F7TVBbZE=
447 | dependencies:
448 | ansi-regex "^2.0.0"
449 |
450 | has-flag@^3.0.0:
451 | version "3.0.0"
452 | resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-3.0.0.tgz#b5d454dc2199ae225699f3467e5a07f3b955bafd"
453 | integrity sha1-tdRU3CGZriJWmfNGfloH87lVuv0=
454 |
455 | has-unicode@^2.0.0:
456 | version "2.0.1"
457 | resolved "https://registry.yarnpkg.com/has-unicode/-/has-unicode-2.0.1.tgz#e0e6fe6a28cf51138855e086d1691e771de2a8b9"
458 | integrity sha1-4Ob+aijPUROIVeCG0Wkedx3iqLk=
459 |
460 | iconv-lite@^0.4.4:
461 | version "0.4.24"
462 | resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.24.tgz#2022b4b25fbddc21d2f524974a474aafe733908b"
463 | integrity sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==
464 | dependencies:
465 | safer-buffer ">= 2.1.2 < 3"
466 |
467 | ignore-walk@^3.0.1:
468 | version "3.0.1"
469 | resolved "https://registry.yarnpkg.com/ignore-walk/-/ignore-walk-3.0.1.tgz#a83e62e7d272ac0e3b551aaa82831a19b69f82f8"
470 | integrity sha512-DTVlMx3IYPe0/JJcYP7Gxg7ttZZu3IInhuEhbchuqneY9wWe5Ojy2mXLBaQFUQmo0AW2r3qG7m1mg86js+gnlQ==
471 | dependencies:
472 | minimatch "^3.0.4"
473 |
474 | inflight@^1.0.4:
475 | version "1.0.6"
476 | resolved "https://registry.yarnpkg.com/inflight/-/inflight-1.0.6.tgz#49bd6331d7d02d0c09bc910a1075ba8165b56df9"
477 | integrity sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=
478 | dependencies:
479 | once "^1.3.0"
480 | wrappy "1"
481 |
482 | inherits@2, inherits@~2.0.3:
483 | version "2.0.3"
484 | resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.3.tgz#633c2c83e3da42a502f52466022480f4208261de"
485 | integrity sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=
486 |
487 | ini@~1.3.0:
488 | version "1.3.5"
489 | resolved "https://registry.yarnpkg.com/ini/-/ini-1.3.5.tgz#eee25f56db1c9ec6085e0c22778083f596abf927"
490 | integrity sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==
491 |
492 | inversify@^5.0.0:
493 | version "5.0.1"
494 | resolved "https://registry.yarnpkg.com/inversify/-/inversify-5.0.1.tgz#500d709b1434896ce5a0d58915c4a4210e34fb6e"
495 | integrity sha512-Ieh06s48WnEYGcqHepdsJUIJUXpwH5o5vodAX+DK2JA/gjy4EbEcQZxw+uFfzysmKjiLXGYwNG3qDZsKVMcINQ==
496 |
497 | invert-kv@^1.0.0:
498 | version "1.0.0"
499 | resolved "https://registry.yarnpkg.com/invert-kv/-/invert-kv-1.0.0.tgz#104a8e4aaca6d3d8cd157a8ef8bfab2d7a3ffdb6"
500 | integrity sha1-EEqOSqym09jNFXqO+L+rLXo//bY=
501 |
502 | is-fullwidth-code-point@^1.0.0:
503 | version "1.0.0"
504 | resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz#ef9e31386f031a7f0d643af82fde50c457ef00cb"
505 | integrity sha1-754xOG8DGn8NZDr4L95QxFfvAMs=
506 | dependencies:
507 | number-is-nan "^1.0.0"
508 |
509 | is-fullwidth-code-point@^2.0.0:
510 | version "2.0.0"
511 | resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz#a3b30a5c4f199183167aaab93beefae3ddfb654f"
512 | integrity sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=
513 |
514 | isarray@0.0.1:
515 | version "0.0.1"
516 | resolved "https://registry.yarnpkg.com/isarray/-/isarray-0.0.1.tgz#8a18acfca9a8f4177e09abfc6038939b05d1eedf"
517 | integrity sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=
518 |
519 | isarray@~1.0.0:
520 | version "1.0.0"
521 | resolved "https://registry.yarnpkg.com/isarray/-/isarray-1.0.0.tgz#bb935d48582cba168c06834957a54a3e07124f11"
522 | integrity sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=
523 |
524 | iterall@^1.2.2:
525 | version "1.2.2"
526 | resolved "https://registry.yarnpkg.com/iterall/-/iterall-1.2.2.tgz#92d70deb8028e0c39ff3164fdbf4d8b088130cd7"
527 | integrity sha512-yynBb1g+RFUPY64fTrFv7nsjRrENBQJaX2UL+2Szc9REFrSNm1rpSXHGzhmAy7a9uv3vlvgBlXnf9RqmPH1/DA==
528 |
529 | js-tokens@^3.0.2:
530 | version "3.0.2"
531 | resolved "https://registry.yarnpkg.com/js-tokens/-/js-tokens-3.0.2.tgz#9866df395102130e38f7f996bceb65443209c25b"
532 | integrity sha1-mGbfOVECEw449/mWvOtlRDIJwls=
533 |
534 | js-yaml@^3.7.0:
535 | version "3.12.1"
536 | resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-3.12.1.tgz#295c8632a18a23e054cf5c9d3cecafe678167600"
537 | integrity sha512-um46hB9wNOKlwkHgiuyEVAybXBjwFUV0Z/RaHJblRd9DXltue9FTYvzCr9ErQrK9Adz5MU4gHWVaNUfdmrC8qA==
538 | dependencies:
539 | argparse "^1.0.7"
540 | esprima "^4.0.0"
541 |
542 | lcid@^1.0.0:
543 | version "1.0.0"
544 | resolved "https://registry.yarnpkg.com/lcid/-/lcid-1.0.0.tgz#308accafa0bc483a3867b4b6f2b9506251d1b835"
545 | integrity sha1-MIrMr6C8SDo4Z7S28rlQYlHRuDU=
546 | dependencies:
547 | invert-kv "^1.0.0"
548 |
549 | lodash.camelcase@^4.3.0:
550 | version "4.3.0"
551 | resolved "https://registry.yarnpkg.com/lodash.camelcase/-/lodash.camelcase-4.3.0.tgz#b28aa6288a2b9fc651035c7711f65ab6190331a6"
552 | integrity sha1-soqmKIorn8ZRA1x3EfZathkDMaY=
553 |
554 | lodash.clone@^4.5.0:
555 | version "4.5.0"
556 | resolved "https://registry.yarnpkg.com/lodash.clone/-/lodash.clone-4.5.0.tgz#195870450f5a13192478df4bc3d23d2dea1907b6"
557 | integrity sha1-GVhwRQ9aExkkeN9Lw9I9LeoZB7Y=
558 |
559 | lodash.forown@^4.4.0:
560 | version "4.4.0"
561 | resolved "https://registry.yarnpkg.com/lodash.forown/-/lodash.forown-4.4.0.tgz#85115cf04f73ef966eced52511d3893cc46683af"
562 | integrity sha1-hRFc8E9z75ZuztUlEdOJPMRmg68=
563 |
564 | lodash@^4.17.10, lodash@^4.17.11, lodash@^4.17.5:
565 | version "4.17.11"
566 | resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.17.11.tgz#b39ea6229ef607ecd89e2c8df12536891cac9b8d"
567 | integrity sha512-cQKh8igo5QUhZ7lg38DYWAxMvjSAKG0A8wGSVimP07SIUEK2UO+arSRKbRZWtelMtN5V0Hkwh5ryOto/SshYIg==
568 |
569 | long@^4.0.0:
570 | version "4.0.0"
571 | resolved "https://registry.yarnpkg.com/long/-/long-4.0.0.tgz#9a7b71cfb7d361a194ea555241c92f7468d5bf28"
572 | integrity sha512-XsP+KhQif4bjX1kbuSiySJFNAehNxgLb6hPRGJ9QsUr8ajHkuXGdrHmFUTUUXhDwVX2R5bY4JNZEwbUiMhV+MA==
573 |
574 | long@~3:
575 | version "3.2.0"
576 | resolved "https://registry.yarnpkg.com/long/-/long-3.2.0.tgz#d821b7138ca1cb581c172990ef14db200b5c474b"
577 | integrity sha1-2CG3E4yhy1gcFymQ7xTbIAtcR0s=
578 |
579 | minimatch@^3.0.4:
580 | version "3.0.4"
581 | resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.0.4.tgz#5166e286457f03306064be5497e8dbb0c3d32083"
582 | integrity sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==
583 | dependencies:
584 | brace-expansion "^1.1.7"
585 |
586 | minimist@0.0.8:
587 | version "0.0.8"
588 | resolved "https://registry.yarnpkg.com/minimist/-/minimist-0.0.8.tgz#857fcabfc3397d2625b8228262e86aa7a011b05d"
589 | integrity sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=
590 |
591 | minimist@^1.2.0:
592 | version "1.2.0"
593 | resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.0.tgz#a35008b20f41383eec1fb914f4cd5df79a264284"
594 | integrity sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=
595 |
596 | minipass@^2.2.1, minipass@^2.3.4:
597 | version "2.3.5"
598 | resolved "https://registry.yarnpkg.com/minipass/-/minipass-2.3.5.tgz#cacebe492022497f656b0f0f51e2682a9ed2d848"
599 | integrity sha512-Gi1W4k059gyRbyVUZQ4mEqLm0YIUiGYfvxhF6SIlk3ui1WVxMTGfGdQ2SInh3PDrRTVvPKgULkpJtT4RH10+VA==
600 | dependencies:
601 | safe-buffer "^5.1.2"
602 | yallist "^3.0.0"
603 |
604 | minizlib@^1.1.1:
605 | version "1.2.1"
606 | resolved "https://registry.yarnpkg.com/minizlib/-/minizlib-1.2.1.tgz#dd27ea6136243c7c880684e8672bb3a45fd9b614"
607 | integrity sha512-7+4oTUOWKg7AuL3vloEWekXY2/D20cevzsrNT2kGWm+39J9hGTCBv8VI5Pm5lXZ/o3/mdR4f8rflAPhnQb8mPA==
608 | dependencies:
609 | minipass "^2.2.1"
610 |
611 | mkdirp@^0.5.0, mkdirp@^0.5.1:
612 | version "0.5.1"
613 | resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-0.5.1.tgz#30057438eac6cf7f8c4767f38648d6697d75c903"
614 | integrity sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=
615 | dependencies:
616 | minimist "0.0.8"
617 |
618 | ms@2.0.0:
619 | version "2.0.0"
620 | resolved "https://registry.yarnpkg.com/ms/-/ms-2.0.0.tgz#5608aeadfc00be6c2901df5f9861788de0d597c8"
621 | integrity sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=
622 |
623 | nan@^2.0.0:
624 | version "2.12.1"
625 | resolved "https://registry.yarnpkg.com/nan/-/nan-2.12.1.tgz#7b1aa193e9aa86057e3c7bbd0ac448e770925552"
626 | integrity sha512-JY7V6lRkStKcKTvHO5NVSQRv+RV+FIL5pvDoLiAtSL9pKlC5x9PKQcZDsq7m4FO4d57mkhC6Z+QhAh3Jdk5JFw==
627 |
628 | needle@^2.2.1:
629 | version "2.2.4"
630 | resolved "https://registry.yarnpkg.com/needle/-/needle-2.2.4.tgz#51931bff82533b1928b7d1d69e01f1b00ffd2a4e"
631 | integrity sha512-HyoqEb4wr/rsoaIDfTH2aVL9nWtQqba2/HvMv+++m8u0dz808MaagKILxtfeSN7QU7nvbQ79zk3vYOJp9zsNEA==
632 | dependencies:
633 | debug "^2.1.2"
634 | iconv-lite "^0.4.4"
635 | sax "^1.2.4"
636 |
637 | node-pre-gyp@^0.12.0:
638 | version "0.12.0"
639 | resolved "https://registry.yarnpkg.com/node-pre-gyp/-/node-pre-gyp-0.12.0.tgz#39ba4bb1439da030295f899e3b520b7785766149"
640 | integrity sha512-4KghwV8vH5k+g2ylT+sLTjy5wmUOb9vPhnM8NHvRf9dHmnW/CndrFXy2aRPaPST6dugXSdHXfeaHQm77PIz/1A==
641 | dependencies:
642 | detect-libc "^1.0.2"
643 | mkdirp "^0.5.1"
644 | needle "^2.2.1"
645 | nopt "^4.0.1"
646 | npm-packlist "^1.1.6"
647 | npmlog "^4.0.2"
648 | rc "^1.2.7"
649 | rimraf "^2.6.1"
650 | semver "^5.3.0"
651 | tar "^4"
652 |
653 | nopt@^4.0.1:
654 | version "4.0.1"
655 | resolved "https://registry.yarnpkg.com/nopt/-/nopt-4.0.1.tgz#d0d4685afd5415193c8c7505602d0d17cd64474d"
656 | integrity sha1-0NRoWv1UFRk8jHUFYC0NF81kR00=
657 | dependencies:
658 | abbrev "1"
659 | osenv "^0.1.4"
660 |
661 | npm-bundled@^1.0.1:
662 | version "1.0.5"
663 | resolved "https://registry.yarnpkg.com/npm-bundled/-/npm-bundled-1.0.5.tgz#3c1732b7ba936b3a10325aef616467c0ccbcc979"
664 | integrity sha512-m/e6jgWu8/v5niCUKQi9qQl8QdeEduFA96xHDDzFGqly0OOjI7c+60KM/2sppfnUU9JJagf+zs+yGhqSOFj71g==
665 |
666 | npm-packlist@^1.1.6:
667 | version "1.2.0"
668 | resolved "https://registry.yarnpkg.com/npm-packlist/-/npm-packlist-1.2.0.tgz#55a60e793e272f00862c7089274439a4cc31fc7f"
669 | integrity sha512-7Mni4Z8Xkx0/oegoqlcao/JpPCPEMtUvsmB0q7mgvlMinykJLSRTYuFqoQLYgGY8biuxIeiHO+QNJKbCfljewQ==
670 | dependencies:
671 | ignore-walk "^3.0.1"
672 | npm-bundled "^1.0.1"
673 |
674 | npmlog@^4.0.2:
675 | version "4.1.2"
676 | resolved "https://registry.yarnpkg.com/npmlog/-/npmlog-4.1.2.tgz#08a7f2a8bf734604779a9efa4ad5cc717abb954b"
677 | integrity sha512-2uUqazuKlTaSI/dC8AzicUck7+IrEaOnN/e0jd3Xtt1KcGpwx30v50mL7oPyr/h9bL3E4aZccVwpwP+5W9Vjkg==
678 | dependencies:
679 | are-we-there-yet "~1.1.2"
680 | console-control-strings "~1.1.0"
681 | gauge "~2.7.3"
682 | set-blocking "~2.0.0"
683 |
684 | number-is-nan@^1.0.0:
685 | version "1.0.1"
686 | resolved "https://registry.yarnpkg.com/number-is-nan/-/number-is-nan-1.0.1.tgz#097b602b53422a522c1afb8790318336941a011d"
687 | integrity sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=
688 |
689 | object-assign@^4.1.0:
690 | version "4.1.1"
691 | resolved "https://registry.yarnpkg.com/object-assign/-/object-assign-4.1.1.tgz#2109adc7965887cfc05cbbd442cac8bfbb360863"
692 | integrity sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=
693 |
694 | once@^1.3.0:
695 | version "1.4.0"
696 | resolved "https://registry.yarnpkg.com/once/-/once-1.4.0.tgz#583b1aa775961d4b113ac17d9c50baef9dd76bd1"
697 | integrity sha1-WDsap3WWHUsROsF9nFC6753Xa9E=
698 | dependencies:
699 | wrappy "1"
700 |
701 | optjs@~3.2.2:
702 | version "3.2.2"
703 | resolved "https://registry.yarnpkg.com/optjs/-/optjs-3.2.2.tgz#69a6ce89c442a44403141ad2f9b370bd5bb6f4ee"
704 | integrity sha1-aabOicRCpEQDFBrS+bNwvVu29O4=
705 |
706 | os-homedir@^1.0.0:
707 | version "1.0.2"
708 | resolved "https://registry.yarnpkg.com/os-homedir/-/os-homedir-1.0.2.tgz#ffbc4988336e0e833de0c168c7ef152121aa7fb3"
709 | integrity sha1-/7xJiDNuDoM94MFox+8VISGqf7M=
710 |
711 | os-locale@^1.4.0:
712 | version "1.4.0"
713 | resolved "https://registry.yarnpkg.com/os-locale/-/os-locale-1.4.0.tgz#20f9f17ae29ed345e8bde583b13d2009803c14d9"
714 | integrity sha1-IPnxeuKe00XoveWDsT0gCYA8FNk=
715 | dependencies:
716 | lcid "^1.0.0"
717 |
718 | os-tmpdir@^1.0.0:
719 | version "1.0.2"
720 | resolved "https://registry.yarnpkg.com/os-tmpdir/-/os-tmpdir-1.0.2.tgz#bbe67406c79aa85c5cfec766fe5734555dfa1274"
721 | integrity sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=
722 |
723 | osenv@^0.1.4:
724 | version "0.1.5"
725 | resolved "https://registry.yarnpkg.com/osenv/-/osenv-0.1.5.tgz#85cdfafaeb28e8677f416e287592b5f3f49ea410"
726 | integrity sha512-0CWcCECdMVc2Rw3U5w9ZjqX6ga6ubk1xDVKxtBQPK7wis/0F2r9T6k4ydGYhecl7YUBxBVxhL5oisPsNxAPe2g==
727 | dependencies:
728 | os-homedir "^1.0.0"
729 | os-tmpdir "^1.0.0"
730 |
731 | path-is-absolute@^1.0.0:
732 | version "1.0.1"
733 | resolved "https://registry.yarnpkg.com/path-is-absolute/-/path-is-absolute-1.0.1.tgz#174b9268735534ffbc7ace6bf53a5a9e1b5c5f5f"
734 | integrity sha1-F0uSaHNVNP+8es5r9TpanhtcX18=
735 |
736 | path-parse@^1.0.6:
737 | version "1.0.6"
738 | resolved "https://registry.yarnpkg.com/path-parse/-/path-parse-1.0.6.tgz#d62dbb5679405d72c4737ec58600e9ddcf06d24c"
739 | integrity sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==
740 |
741 | process-nextick-args@~2.0.0:
742 | version "2.0.0"
743 | resolved "https://registry.yarnpkg.com/process-nextick-args/-/process-nextick-args-2.0.0.tgz#a37d732f4271b4ab1ad070d35508e8290788ffaa"
744 | integrity sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==
745 |
746 | promisify-call@^2.0.0:
747 | version "2.0.4"
748 | resolved "https://registry.yarnpkg.com/promisify-call/-/promisify-call-2.0.4.tgz#d48c2d45652ccccd52801ddecbd533a6d4bd5fba"
749 | integrity sha1-1IwtRWUszM1SgB3ey9UzptS9X7o=
750 | dependencies:
751 | with-callback "^1.0.2"
752 |
753 | protobufjs@^5.0.3:
754 | version "5.0.3"
755 | resolved "https://registry.yarnpkg.com/protobufjs/-/protobufjs-5.0.3.tgz#e4dfe9fb67c90b2630d15868249bcc4961467a17"
756 | integrity sha512-55Kcx1MhPZX0zTbVosMQEO5R6/rikNXd9b6RQK4KSPcrSIIwoXTtebIczUrXlwaSrbz4x8XUVThGPob1n8I4QA==
757 | dependencies:
758 | ascli "~1"
759 | bytebuffer "~5"
760 | glob "^7.0.5"
761 | yargs "^3.10.0"
762 |
763 | protobufjs@^6.8.6, protobufjs@^6.8.8:
764 | version "6.8.8"
765 | resolved "https://registry.yarnpkg.com/protobufjs/-/protobufjs-6.8.8.tgz#c8b4f1282fd7a90e6f5b109ed11c84af82908e7c"
766 | integrity sha512-AAmHtD5pXgZfi7GMpllpO3q1Xw1OYldr+dMUlAnffGTAhqkg72WdmSY71uKBF/JuyiKs8psYbtKrhi0ASCD8qw==
767 | dependencies:
768 | "@protobufjs/aspromise" "^1.1.2"
769 | "@protobufjs/base64" "^1.1.2"
770 | "@protobufjs/codegen" "^2.0.4"
771 | "@protobufjs/eventemitter" "^1.1.0"
772 | "@protobufjs/fetch" "^1.1.0"
773 | "@protobufjs/float" "^1.0.2"
774 | "@protobufjs/inquire" "^1.1.0"
775 | "@protobufjs/path" "^1.1.2"
776 | "@protobufjs/pool" "^1.1.0"
777 | "@protobufjs/utf8" "^1.1.0"
778 | "@types/long" "^4.0.0"
779 | "@types/node" "^10.1.0"
780 | long "^4.0.0"
781 |
782 | rc@^1.2.7:
783 | version "1.2.8"
784 | resolved "https://registry.yarnpkg.com/rc/-/rc-1.2.8.tgz#cd924bf5200a075b83c188cd6b9e211b7fc0d3ed"
785 | integrity sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==
786 | dependencies:
787 | deep-extend "^0.6.0"
788 | ini "~1.3.0"
789 | minimist "^1.2.0"
790 | strip-json-comments "~2.0.1"
791 |
792 | readable-stream@^2.0.6:
793 | version "2.3.6"
794 | resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-2.3.6.tgz#b11c27d88b8ff1fbe070643cf94b0c79ae1b0aaf"
795 | integrity sha512-tQtKA9WIAhBF3+VLAseyMqZeBjW0AHJoxOtYqSUZNJxauErmLbVm2FW1y+J/YA9dUrAC39ITejlZWhVIwawkKw==
796 | dependencies:
797 | core-util-is "~1.0.0"
798 | inherits "~2.0.3"
799 | isarray "~1.0.0"
800 | process-nextick-args "~2.0.0"
801 | safe-buffer "~5.1.1"
802 | string_decoder "~1.1.1"
803 | util-deprecate "~1.0.1"
804 |
805 | reflect-metadata@^0.1.12:
806 | version "0.1.12"
807 | resolved "https://registry.yarnpkg.com/reflect-metadata/-/reflect-metadata-0.1.12.tgz#311bf0c6b63cd782f228a81abe146a2bfa9c56f2"
808 | integrity sha512-n+IyV+nGz3+0q3/Yf1ra12KpCyi001bi4XFxSjbiWWjfqb52iTTtpGXmCCAOWWIAn9KEuFZKGqBERHmrtScZ3A==
809 |
810 | resolve@^1.3.2:
811 | version "1.9.0"
812 | resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.9.0.tgz#a14c6fdfa8f92a7df1d996cb7105fa744658ea06"
813 | integrity sha512-TZNye00tI67lwYvzxCxHGjwTNlUV70io54/Ed4j6PscB8xVfuBJpRenI/o6dVk0cY0PYTY27AgCoGGxRnYuItQ==
814 | dependencies:
815 | path-parse "^1.0.6"
816 |
817 | rimraf@^2.6.1:
818 | version "2.6.3"
819 | resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-2.6.3.tgz#b2d104fe0d8fb27cf9e0a1cda8262dd3833c6cab"
820 | integrity sha512-mwqeW5XsA2qAejG46gYdENaxXjx9onRNCfn7L0duuP4hCuTIi/QO7PDK07KJfp1d+izWPrzEJDcSqBa0OZQriA==
821 | dependencies:
822 | glob "^7.1.3"
823 |
824 | safe-buffer@^5.1.2, safe-buffer@~5.1.0, safe-buffer@~5.1.1:
825 | version "5.1.2"
826 | resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.1.2.tgz#991ec69d296e0313747d59bdfd2b745c35f8828d"
827 | integrity sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==
828 |
829 | "safer-buffer@>= 2.1.2 < 3":
830 | version "2.1.2"
831 | resolved "https://registry.yarnpkg.com/safer-buffer/-/safer-buffer-2.1.2.tgz#44fa161b0187b9549dd84bb91802f9bd8385cd6a"
832 | integrity sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==
833 |
834 | sax@^1.2.4:
835 | version "1.2.4"
836 | resolved "https://registry.yarnpkg.com/sax/-/sax-1.2.4.tgz#2816234e2378bddc4e5354fab5caa895df7100d9"
837 | integrity sha512-NqVDv9TpANUjFm0N8uM5GxL36UgKi9/atZw+x7YFnQ8ckwFGKrl4xX4yWtrey3UJm5nP1kUbnYgLopqWNSRhWw==
838 |
839 | semver@^5.3.0:
840 | version "5.6.0"
841 | resolved "https://registry.yarnpkg.com/semver/-/semver-5.6.0.tgz#7e74256fbaa49c75aa7c7a205cc22799cac80004"
842 | integrity sha512-RS9R6R35NYgQn++fkDWaOmqGoj4Ek9gGs+DPxNUZKuwE183xjJroKvyo1IzVFeXvUrvmALy6FWD5xrdJT25gMg==
843 |
844 | set-blocking@~2.0.0:
845 | version "2.0.0"
846 | resolved "https://registry.yarnpkg.com/set-blocking/-/set-blocking-2.0.0.tgz#045f9782d011ae9a6803ddd382b24392b3d890f7"
847 | integrity sha1-BF+XgtARrppoA93TgrJDkrPYkPc=
848 |
849 | signal-exit@^3.0.0:
850 | version "3.0.2"
851 | resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.2.tgz#b5fdc08f1287ea1178628e415e25132b73646c6d"
852 | integrity sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=
853 |
854 | sprintf-js@~1.0.2:
855 | version "1.0.3"
856 | resolved "https://registry.yarnpkg.com/sprintf-js/-/sprintf-js-1.0.3.tgz#04e6926f662895354f3dd015203633b857297e2c"
857 | integrity sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=
858 |
859 | string-width@^1.0.1:
860 | version "1.0.2"
861 | resolved "https://registry.yarnpkg.com/string-width/-/string-width-1.0.2.tgz#118bdf5b8cdc51a2a7e70d211e07e2b0b9b107d3"
862 | integrity sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=
863 | dependencies:
864 | code-point-at "^1.0.0"
865 | is-fullwidth-code-point "^1.0.0"
866 | strip-ansi "^3.0.0"
867 |
868 | "string-width@^1.0.2 || 2":
869 | version "2.1.1"
870 | resolved "https://registry.yarnpkg.com/string-width/-/string-width-2.1.1.tgz#ab93f27a8dc13d28cac815c462143a6d9012ae9e"
871 | integrity sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==
872 | dependencies:
873 | is-fullwidth-code-point "^2.0.0"
874 | strip-ansi "^4.0.0"
875 |
876 | string_decoder@~1.1.1:
877 | version "1.1.1"
878 | resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.1.1.tgz#9cf1611ba62685d7030ae9e4ba34149c3af03fc8"
879 | integrity sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==
880 | dependencies:
881 | safe-buffer "~5.1.0"
882 |
883 | strip-ansi@^3.0.0, strip-ansi@^3.0.1:
884 | version "3.0.1"
885 | resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-3.0.1.tgz#6a385fb8853d952d5ff05d0e8aaf94278dc63dcf"
886 | integrity sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=
887 | dependencies:
888 | ansi-regex "^2.0.0"
889 |
890 | strip-ansi@^4.0.0:
891 | version "4.0.0"
892 | resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-4.0.0.tgz#a8479022eb1ac368a871389b635262c505ee368f"
893 | integrity sha1-qEeQIusaw2iocTibY1JixQXuNo8=
894 | dependencies:
895 | ansi-regex "^3.0.0"
896 |
897 | strip-json-comments@~2.0.1:
898 | version "2.0.1"
899 | resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-2.0.1.tgz#3c531942e908c2697c0ec344858c286c7ca0a60a"
900 | integrity sha1-PFMZQukIwml8DsNEhYwobHygpgo=
901 |
902 | supports-color@^2.0.0:
903 | version "2.0.0"
904 | resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-2.0.0.tgz#535d045ce6b6363fa40117084629995e9df324c7"
905 | integrity sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=
906 |
907 | supports-color@^5.3.0:
908 | version "5.5.0"
909 | resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-5.5.0.tgz#e2e69a44ac8772f78a1ec0b35b689df6530efc8f"
910 | integrity sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==
911 | dependencies:
912 | has-flag "^3.0.0"
913 |
914 | tar@^4:
915 | version "4.4.8"
916 | resolved "https://registry.yarnpkg.com/tar/-/tar-4.4.8.tgz#b19eec3fde2a96e64666df9fdb40c5ca1bc3747d"
917 | integrity sha512-LzHF64s5chPQQS0IYBn9IN5h3i98c12bo4NCO7e0sGM2llXQ3p2FGC5sdENN4cTW48O915Sh+x+EXx7XW96xYQ==
918 | dependencies:
919 | chownr "^1.1.1"
920 | fs-minipass "^1.2.5"
921 | minipass "^2.3.4"
922 | minizlib "^1.1.1"
923 | mkdirp "^0.5.0"
924 | safe-buffer "^5.1.2"
925 | yallist "^3.0.2"
926 |
927 | traverse@^0.6.6:
928 | version "0.6.6"
929 | resolved "https://registry.yarnpkg.com/traverse/-/traverse-0.6.6.tgz#cbdf560fd7b9af632502fed40f918c157ea97137"
930 | integrity sha1-y99WD9e5r2MlAv7UD5GMFX6pcTc=
931 |
932 | tslib@1.9.0:
933 | version "1.9.0"
934 | resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.9.0.tgz#e37a86fda8cbbaf23a057f473c9f4dc64e5fc2e8"
935 | integrity sha512-f/qGG2tUkrISBlQZEjEqoZ3B2+npJjIf04H1wuAv9iA8i04Icp+61KRXxFdha22670NJopsZCIjhC3SnjPRKrQ==
936 |
937 | tslib@^1.7.1, tslib@^1.8.0, tslib@^1.8.1:
938 | version "1.9.3"
939 | resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.9.3.tgz#d7e4dd79245d85428c4d7e4822a79917954ca286"
940 | integrity sha512-4krF8scpejhaOgqzBEcGM7yDIEfi0/8+8zDRZhNZZ2kjmHJ4hv3zCbQWxoJGz1iw5U0Jl0nma13xzHXcncMavQ==
941 |
942 | tslint-config-airbnb@^5.11.1:
943 | version "5.11.1"
944 | resolved "https://registry.yarnpkg.com/tslint-config-airbnb/-/tslint-config-airbnb-5.11.1.tgz#51a27fbb8bf24c144d064a274a71da47e7ece617"
945 | integrity sha512-hkaittm2607vVMe8eotANGN1CimD5tor7uoY3ypg2VTtEcDB/KGWYbJOz58t8LI4cWSyWtgqYQ5F0HwKxxhlkQ==
946 | dependencies:
947 | tslint-consistent-codestyle "^1.14.1"
948 | tslint-eslint-rules "^5.4.0"
949 | tslint-microsoft-contrib "~5.2.1"
950 |
951 | tslint-consistent-codestyle@^1.14.1:
952 | version "1.15.0"
953 | resolved "https://registry.yarnpkg.com/tslint-consistent-codestyle/-/tslint-consistent-codestyle-1.15.0.tgz#a3acf8d0a3ca0dc7d1285705102ba1fe4a17c4cb"
954 | integrity sha512-6BNDBbZh2K0ibRXe70Mkl9gfVttxQ3t3hqV1BRDfpIcjrUoOgD946iH4SrXp+IggDgeMs3dJORjD5tqL5j4jXg==
955 | dependencies:
956 | "@fimbul/bifrost" "^0.17.0"
957 | tslib "^1.7.1"
958 | tsutils "^2.29.0"
959 |
960 | tslint-eslint-rules@^5.4.0:
961 | version "5.4.0"
962 | resolved "https://registry.yarnpkg.com/tslint-eslint-rules/-/tslint-eslint-rules-5.4.0.tgz#e488cc9181bf193fe5cd7bfca213a7695f1737b5"
963 | integrity sha512-WlSXE+J2vY/VPgIcqQuijMQiel+UtmXS+4nvK4ZzlDiqBfXse8FAvkNnTcYhnQyOTW5KFM+uRRGXxYhFpuBc6w==
964 | dependencies:
965 | doctrine "0.7.2"
966 | tslib "1.9.0"
967 | tsutils "^3.0.0"
968 |
969 | tslint-microsoft-contrib@~5.2.1:
970 | version "5.2.1"
971 | resolved "https://registry.yarnpkg.com/tslint-microsoft-contrib/-/tslint-microsoft-contrib-5.2.1.tgz#a6286839f800e2591d041ea2800c77487844ad81"
972 | integrity sha512-PDYjvpo0gN9IfMULwKk0KpVOPMhU6cNoT9VwCOLeDl/QS8v8W2yspRpFFuUS7/c5EIH/n8ApMi8TxJAz1tfFUA==
973 | dependencies:
974 | tsutils "^2.27.2 <2.29.0"
975 |
976 | tslint@^5.12.1:
977 | version "5.12.1"
978 | resolved "https://registry.yarnpkg.com/tslint/-/tslint-5.12.1.tgz#8cec9d454cf8a1de9b0a26d7bdbad6de362e52c1"
979 | integrity sha512-sfodBHOucFg6egff8d1BvuofoOQ/nOeYNfbp7LDlKBcLNrL3lmS5zoiDGyOMdT7YsEXAwWpTdAHwOGOc8eRZAw==
980 | dependencies:
981 | babel-code-frame "^6.22.0"
982 | builtin-modules "^1.1.1"
983 | chalk "^2.3.0"
984 | commander "^2.12.1"
985 | diff "^3.2.0"
986 | glob "^7.1.1"
987 | js-yaml "^3.7.0"
988 | minimatch "^3.0.4"
989 | resolve "^1.3.2"
990 | semver "^5.3.0"
991 | tslib "^1.8.0"
992 | tsutils "^2.27.2"
993 |
994 | tsutils@^2.27.2, tsutils@^2.29.0:
995 | version "2.29.0"
996 | resolved "https://registry.yarnpkg.com/tsutils/-/tsutils-2.29.0.tgz#32b488501467acbedd4b85498673a0812aca0b99"
997 | integrity sha512-g5JVHCIJwzfISaXpXE1qvNalca5Jwob6FjI4AoPlqMusJ6ftFE7IkkFoMhVLRgK+4Kx3gkzb8UZK5t5yTTvEmA==
998 | dependencies:
999 | tslib "^1.8.1"
1000 |
1001 | "tsutils@^2.27.2 <2.29.0":
1002 | version "2.28.0"
1003 | resolved "https://registry.yarnpkg.com/tsutils/-/tsutils-2.28.0.tgz#6bd71e160828f9d019b6f4e844742228f85169a1"
1004 | integrity sha512-bh5nAtW0tuhvOJnx1GLRn5ScraRLICGyJV5wJhtRWOLsxW70Kk5tZtpK3O/hW6LDnqKS9mlUMPZj9fEMJ0gxqA==
1005 | dependencies:
1006 | tslib "^1.8.1"
1007 |
1008 | tsutils@^3.0.0, tsutils@^3.5.0:
1009 | version "3.7.0"
1010 | resolved "https://registry.yarnpkg.com/tsutils/-/tsutils-3.7.0.tgz#f97bdd2f109070bd1865467183e015b25734b477"
1011 | integrity sha512-n+e+3q7Jx2kfZw7tjfI9axEIWBY0sFMOlC+1K70X0SeXpO/UYSB+PN+E9tIJNqViB7oiXQdqD7dNchnvoneZew==
1012 | dependencies:
1013 | tslib "^1.8.1"
1014 |
1015 | typescript@^3.2.2:
1016 | version "3.2.2"
1017 | resolved "https://registry.yarnpkg.com/typescript/-/typescript-3.2.2.tgz#fe8101c46aa123f8353523ebdcf5730c2ae493e5"
1018 | integrity sha512-VCj5UiSyHBjwfYacmDuc/NOk4QQixbE+Wn7MFJuS0nRuPQbof132Pw4u53dm264O8LPc2MVsc7RJNml5szurkg==
1019 |
1020 | util-deprecate@~1.0.1:
1021 | version "1.0.2"
1022 | resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf"
1023 | integrity sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=
1024 |
1025 | wide-align@^1.1.0:
1026 | version "1.1.3"
1027 | resolved "https://registry.yarnpkg.com/wide-align/-/wide-align-1.1.3.tgz#ae074e6bdc0c14a431e804e624549c633b000457"
1028 | integrity sha512-QGkOQc8XL6Bt5PwnsExKBPuMKBxnGxWWW3fU55Xt4feHozMUhdUMaBCk290qpm/wG5u/RSKzwdAC4i51YigihA==
1029 | dependencies:
1030 | string-width "^1.0.2 || 2"
1031 |
1032 | window-size@^0.1.4:
1033 | version "0.1.4"
1034 | resolved "https://registry.yarnpkg.com/window-size/-/window-size-0.1.4.tgz#f8e1aa1ee5a53ec5bf151ffa09742a6ad7697876"
1035 | integrity sha1-+OGqHuWlPsW/FR/6CXQqatdpeHY=
1036 |
1037 | with-callback@^1.0.2:
1038 | version "1.0.2"
1039 | resolved "https://registry.yarnpkg.com/with-callback/-/with-callback-1.0.2.tgz#a09629b9a920028d721404fb435bdcff5c91bc21"
1040 | integrity sha1-oJYpuakgAo1yFAT7Q1vc/1yRvCE=
1041 |
1042 | wrap-ansi@^2.0.0:
1043 | version "2.1.0"
1044 | resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-2.1.0.tgz#d8fc3d284dd05794fe84973caecdd1cf824fdd85"
1045 | integrity sha1-2Pw9KE3QV5T+hJc8rs3Rz4JP3YU=
1046 | dependencies:
1047 | string-width "^1.0.1"
1048 | strip-ansi "^3.0.1"
1049 |
1050 | wrappy@1:
1051 | version "1.0.2"
1052 | resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f"
1053 | integrity sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=
1054 |
1055 | y18n@^3.2.0:
1056 | version "3.2.1"
1057 | resolved "https://registry.yarnpkg.com/y18n/-/y18n-3.2.1.tgz#6d15fba884c08679c0d77e88e7759e811e07fa41"
1058 | integrity sha1-bRX7qITAhnnA136I53WegR4H+kE=
1059 |
1060 | yallist@^3.0.0, yallist@^3.0.2:
1061 | version "3.0.3"
1062 | resolved "https://registry.yarnpkg.com/yallist/-/yallist-3.0.3.tgz#b4b049e314be545e3ce802236d6cd22cd91c3de9"
1063 | integrity sha512-S+Zk8DEWE6oKpV+vI3qWkaK+jSbIK86pCwe2IF/xwIpQ8jEuxpw9NyaGjmp9+BoJv5FV2piqCDcoCtStppiq2A==
1064 |
1065 | yargs@^3.10.0:
1066 | version "3.32.0"
1067 | resolved "https://registry.yarnpkg.com/yargs/-/yargs-3.32.0.tgz#03088e9ebf9e756b69751611d2a5ef591482c995"
1068 | integrity sha1-AwiOnr+edWtpdRYR0qXvWRSCyZU=
1069 | dependencies:
1070 | camelcase "^2.0.1"
1071 | cliui "^3.0.3"
1072 | decamelize "^1.1.1"
1073 | os-locale "^1.4.0"
1074 | string-width "^1.0.1"
1075 | window-size "^0.1.4"
1076 | y18n "^3.2.0"
1077 |
--------------------------------------------------------------------------------