最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

Nodejs開發(fā)grpc的實(shí)例代碼

 更新時(shí)間:2024年10月16日 09:44:30   作者:mazhongjia  
Nodejs開發(fā)grpc包含靜態(tài)和動(dòng)態(tài)兩種代碼生成方式,靜態(tài)代碼生成需要提前通過.proto文件編譯生成JS源碼,而動(dòng)態(tài)代碼生成則是在運(yùn)行時(shí)指定IDL文件位置,實(shí)時(shí)生成源碼,兩者各有優(yōu)缺點(diǎn),本文給大家介紹Nodejs開發(fā)grpc的實(shí)例代碼,感興趣的朋友一起看看吧

nodejs開發(fā)grpc示例

Nodejs開發(fā)grpc有兩種方式(與其他語言開發(fā)方式不同)

  • 靜態(tài)代碼生成:與傳統(tǒng)方式一樣,提前編譯生成好js源碼,開發(fā)時(shí)就可以應(yīng)用生成js文件中源碼。
  • 動(dòng)態(tài)代碼生成:不需要提前由.proto文件(IDL文件)生成js代碼,而是通過提前指定好IDL文件的位置,運(yùn)行時(shí)再生成對(duì)應(yīng)的源碼文件。

哪個(gè)好,哪個(gè)不好?沒有明確規(guī)則,但是一個(gè)最佳實(shí)踐:要么全部動(dòng)態(tài)生成、要么全部靜態(tài)生成,不然容易錯(cuò)亂。

開發(fā)nodejs,工程路徑?jīng)]有嚴(yán)格要求,這里在工程根目錄下:

  • 創(chuàng)建app文件存放我們開發(fā)的js源碼
  • 創(chuàng)建proto文件存放IDL文件
  • 由于nodejs是異步框架,所以編寫nodejs代碼絕大多數(shù)都是通過回調(diào)、通知、事件的方式獲取對(duì)端的響應(yīng)

一、動(dòng)態(tài)代碼生成

可見,代碼中僅僅指定了IDL文件的路徑,通過對(duì)應(yīng)的gprc的load方法加載這個(gè)文件,全程沒有用到grpc的編譯工具生成相關(guān)代碼。

工程結(jié)構(gòu):

這里是一個(gè)grpc的nodejs客戶端與服務(wù)端實(shí)現(xiàn),首先是服務(wù)端代碼

//定義一個(gè)常量指定proto文件路徑
var PROTO_FILE_PATH = 'E:\\01.study\\36.nodejs\\workspace\\grpc-demo\\proto\\Student.proto';
//引入GRPC庫
var grpc = require('grpc');
//找到我們在IDL文件中定義的service:StudentService
var grpcService = grpc.load(PROTO_FILE_PATH).com.mzj.netty.ssy._08_grpc;
//定義服務(wù)端
var server = new grpc.Server();
server.addService(grpcService.StudentService.service,{
    //添加測試的rpc方法,服務(wù)名:服務(wù)對(duì)應(yīng)調(diào)用方法
    getRealNameByUsername: getRealNameByUsername1,
    // 添加其他rpc方法
    getStudentsByAge: getStudentsByAge1,
    getStudentsWrapperByAges: getStudentsWrapperByAges1,
    biTalk: biTalk1,
})
//綁定端口,并設(shè)置不是用ssl安全加密
server.bind('localhost:8899',grpc.ServerCredentials.createInsecure());
//啟動(dòng)服務(wù)器
server.start();
//實(shí)現(xiàn)rpc服務(wù)調(diào)用處理函數(shù):參數(shù)1call:請(qǐng)求對(duì)象,參數(shù)2callback:回調(diào)函數(shù)
function getRealNameByUsername1(call,callback) {
    console.log("username : " + call.request.username);//打印請(qǐng)求對(duì)象
    /**
     * 定義回調(diào)函數(shù)
     */
    callback(null,{realname: 'mazhongjia'});//參數(shù)1:錯(cuò)誤對(duì)象,這里不進(jìn)行設(shè)置,參數(shù)2:返回給客戶端的結(jié)果對(duì)象,這里的屬性名對(duì)應(yīng)IDL中聲明的屬性名
}
function getStudentsByAge1(){
}
function getStudentsWrapperByAges1(){
}
function biTalk1(){
}
 

然后是客戶端代碼:

//--------------動(dòng)態(tài)代碼生成的方式:--------------
//1、定義grpc的IDL文件位置
var PROTO_FILE_PATH = 'E:\\01.study\\36.nodejs\\workspace\\grpc-demo\\proto\\Student.proto';
//2、引入grpc庫,nodejs中,引入庫用require方法
var grpc = require('grpc');
//3、定義grpc服務(wù)
//找到我們在IDL文件中定義的service:StudentService
var grpcService = grpc.load(PROTO_FILE_PATH).com.mzj.netty.ssy._08_grpc;
//4、定義nodejs客戶端
var client = new grpcService.StudentService('localhost:8899',grpc.credentials.createInsecure());
//grpc.credentials.createInsecure():創(chuàng)建的是一個(gè)不安全的、不是用ssl證書加密的通道,與java如下代碼等價(jià):
//.usePlaintext(true).
//調(diào)用rpc方法,其中方法首字母轉(zhuǎn)小寫
client.getRealNameByUsername({username:'lisi'},function (error,respData) {
    console.log(respData);
})
 

grpc的IDL文件:

syntax = "proto3";
package com.mzj.netty.ssy._08_grpc;
option java_package = "com.mzj.netty.ssy._08_grpc";
option java_outer_classname = "StudentProto";
option java_multiple_files = true;
service StudentService{
    //gRpc支持的四種調(diào)用形式示例:
    rpc GetRealNameByUsername(MyRequest) returns (MyResponse){}//種類1:普通輸入?yún)?shù)與返回值
    rpc GetStudentsByAge(StudentRequest) returns (stream StudentResponse){}//種類2:服務(wù)端rpc方法返回值是stream形式,參數(shù)是普通對(duì)象
    rpc GetStudentsWrapperByAges(stream StudentRequest) returns (StudentResponseList){}//種類3:客戶端輸入?yún)?shù)是stream形式,返回是一個(gè)普通對(duì)象
    rpc BiTalk(stream StreamRequest) returns (stream StreamResponse){}//種類4:雙向的流式的數(shù)據(jù)傳遞(客戶端發(fā)送請(qǐng)求/服務(wù)端返回結(jié)果都是流式)
    //從IDL的定義上,四種調(diào)用形式區(qū)別體現(xiàn)在rpc定義時(shí)方法參數(shù)、返回值的message前面是否有stream關(guān)鍵字
    //rpc方法的參數(shù)與返回值類型都是IDL中定義的message類型,而不能是string、int32等變量類型,這一點(diǎn)跟thrift不同,即使只有一個(gè)屬性,也得定義成message
}
message MyRequest{
    string username = 1;
}
message MyResponse{
    string realname = 2;
}
message StudentRequest{
    int32 age = 1;
}
message StudentResponse{
    string name = 1;
    int32 age = 2;
    string city = 3;
}
message StudentResponseList{
    //protobuf中集合用repeated表示
    repeated StudentResponse studentResponse = 1;//repeated表示集合類型,這里表示服務(wù)器端向客戶端返回的是一個(gè)集合類型,集合中元素是StudentResponse
}
message StreamRequest{
    string request_info = 1;
}
message StreamResponse{
    string response_info = 1;
}

分別運(yùn)行服務(wù)端、客戶端代碼。

二、靜態(tài)代碼生成

1、說明:通過grpc編譯器protoc預(yù)先生成js源碼,然后編碼過程中顯示調(diào)用。

2、具體操作方式:按照官網(wǎng)示例

https://github.com/grpc/grpc/tree/v1.4.x/examples/node/static_codegen

下面內(nèi)容參考的是上面網(wǎng)址的README.md文件

步驟1:安裝grpc-tools,通過nodejs的npm包管理工具按照grpc-tools插件

npm install -g grpc-tools

步驟2:通過編譯器生成對(duì)應(yīng)nodejs源碼:

下面是readme文件中原始命令,需要進(jìn)行修改

grpc_tools_node_protoc --js_out=import_style=commonjs,binary:../node/static_codegen/ --grpc_out=../node/static_codegen --plugin=protoc-gen-grpc=`which grpc_tools_node_protoc_plugin` helloworld.proto

修改后實(shí)際執(zhí)行的為:

grpc_tools_node_protoc --js_out=import_style=commonjs,binary:static_codegen/ --grpc_out=static_codegen --plugin=protoc-gen-grpc=/c/Users/mzj/AppData/Roaming/npm/grpc_tools_node_protoc_plugin.cmd proto/Student.proto

其中兩個(gè)路徑分別是生成的消息源碼路徑和grpc通信源碼路徑,我們修改成生成到相同的路徑

其中/c/Users/mzj/AppData/Roaming/npm/grpc_tools_node_protoc_plugin是通過執(zhí)行原始命令中which grpc_tools_node_protoc_plugin得到的,但是后面需要加上.cmd:

執(zhí)行后出錯(cuò):

提示沒有這個(gè)目錄,手工創(chuàng)建后再執(zhí)行,則OK

生成代碼如下:

其中這兩個(gè)文件:Student_pb.js是消息相關(guān)源碼,Student_grpc_pb.js是grpc相關(guān)通信代碼(與java生成源碼類似,也是消息+grpc通信兩部分)

編寫客戶端代碼:

//1、定義service,service位于Student_grpc_pb.js中
var service = require('../static_codegen/proto/Student_grpc_pb.js');
//2、定義消息
var message = require('../static_codegen/proto/Student_pb.js');
//3、引入grpc庫
var grpc = require('grpc');
//4、定義客戶端
var client = new service.StudentServiceClient('localhost:8899',grpc.credentials.createInsecure());
//5、定義請(qǐng)求message(與動(dòng)態(tài)生成方式不同)
var request = new message.MyRequest();
request.setUsername('huna');
//6、調(diào)用rpc方法
client.getRealNameByUsername(request,function (error,respData) {
    //靜態(tài)調(diào)用方式是以方法調(diào)用的方式獲取返回結(jié)果,因?yàn)閞pc的返回值在編譯期可見,而動(dòng)態(tài)方式rpc返回值編輯期不可見、是通過屬性的方式獲取結(jié)果
    console.log(respData.getRealname());//打印返回結(jié)果
})

測試:啟動(dòng)動(dòng)態(tài)代碼生成編寫的服務(wù)端、啟動(dòng)靜態(tài)代碼生成的客戶端。

靜態(tài)代碼生成方式編寫的服務(wù)端:

總結(jié)動(dòng)態(tài)與靜態(tài)代碼生成方式優(yōu)缺點(diǎn): 靜態(tài)與動(dòng)態(tài)方式使用場景,到底使用哪種(視頻31_30分鐘)動(dòng)態(tài)方式好處:不需要預(yù)先生成源碼文件動(dòng)態(tài)方式缺陷:編寫代碼階段無法獲取具體有哪些屬性,只能自己保證編寫代碼屬性的正確性,無法在編譯期保證正確性,同時(shí)可讀性不好靜態(tài)方式好處:每一個(gè)對(duì)象有什么方法,編寫代碼階段都能看到,代碼可讀性好靜態(tài)方式缺點(diǎn):較動(dòng)態(tài)方式麻煩我推薦使用靜態(tài)代碼生成的方式:因?yàn)榇a編寫過程中一些代碼編寫提示與可讀性更重要,而自動(dòng)生成代碼可以通過編寫腳步實(shí)現(xiàn)自動(dòng)化。

到此這篇關(guān)于Nodejs開發(fā)grpc的文章就介紹到這了,更多相關(guān)Nodejs開發(fā)grpc內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • 使用nvm管理多版本node的詳細(xì)教程

    使用nvm管理多版本node的詳細(xì)教程

    在開發(fā)工作中,經(jīng)常在不同的項(xiàng)目中使用不同版本的node去開發(fā),換一個(gè)項(xiàng)目在重新安裝node太麻煩,所以使用nvm來管理多版本的node開發(fā)環(huán)境,就非常方便了,所以本文給大家介紹了如何使用nvm管理多版本node,需要的朋友可以參考下
    2024-08-08
  • 使用NVM管理和控制Node版本的具體教程

    使用NVM管理和控制Node版本的具體教程

    在現(xiàn)代 JavaScript 開發(fā)中,Node.js 是一個(gè)非常重要的工具,由于項(xiàng)目的需求不同,開發(fā)人員可能會(huì)需要在不同的 Node.js 版本之間切換,這時(shí) nvm便成為了一個(gè)非常方便的工具,本文將介紹如何使用 nvm 來管理和控制 Node.js 版本,需要的朋友可以參考下
    2025-05-05
  • 詳解基于Koa2開發(fā)微信二維碼掃碼支付相關(guān)流程

    詳解基于Koa2開發(fā)微信二維碼掃碼支付相關(guān)流程

    這篇文章主要介紹了詳解基于Koa2開發(fā)微信二維碼掃碼支付相關(guān)流程,小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧
    2018-05-05
  • 淺談node.js中async異步編程

    淺談node.js中async異步編程

    本文嘗試結(jié)合Marc Fasel的指導(dǎo)思想和筆者的實(shí)踐經(jīng)驗(yàn)來介紹一些NodeJS的異步編程風(fēng)格,希望對(duì)NodeJS的初學(xué)者有所啟發(fā)。
    2015-10-10
  • node.js 模塊和其下載資源的鏡像設(shè)置的方法

    node.js 模塊和其下載資源的鏡像設(shè)置的方法

    這篇文章主要介紹了node.js 模塊和其下載資源的鏡像設(shè)置的方法,在設(shè)置淘寶鏡像共有三種方法,每種方法通過實(shí)例代碼給大家介紹的非常詳細(xì),具有一定的參考借鑒價(jià)值 ,需要的朋友可以參考下
    2018-09-09
  • Nodejs下用submit提交表單提示cannot post錯(cuò)誤的解決方法

    Nodejs下用submit提交表單提示cannot post錯(cuò)誤的解決方法

    這篇文章主要介紹了Nodejs下用submit提交表單提示cannot post錯(cuò)誤的解決方法,非常不錯(cuò),具有參考借鑒價(jià)值,感興趣的朋友一起看看吧
    2016-11-11
  • 深入解析Node.js中save-dev命令的具體使用

    深入解析Node.js中save-dev命令的具體使用

    本文詳細(xì)介紹了npm的--save-dev選項(xiàng)及其在前端開發(fā)中的應(yīng)用,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2024-12-12
  • Node.js本地文件操作之文件拷貝與目錄遍歷的方法

    Node.js本地文件操作之文件拷貝與目錄遍歷的方法

    這篇文章主要介紹了Node.js本地文件操作之文件拷貝與目錄遍歷的方法,拷貝用到了Node的文件API,遍歷則舉了一個(gè)異步API實(shí)現(xiàn)的形式(Node的一大特點(diǎn)),需要的朋友可以參考下
    2016-02-02
  • 詳談nodejs異步編程

    詳談nodejs異步編程

    本文詳細(xì)介紹了node.js異步編程的分類以及異步編程存在的問題,非常的詳盡,非常細(xì)致,這里推薦給小伙伴。
    2014-12-12
  • Nodejs異步回調(diào)之異常處理實(shí)例分析

    Nodejs異步回調(diào)之異常處理實(shí)例分析

    這篇文章主要介紹了Nodejs異步回調(diào)之異常處理,結(jié)合實(shí)例形式分析了nodejs基于中間件進(jìn)行異步回調(diào)異常處理過程出現(xiàn)的問題與相應(yīng)的解決方法,需要的朋友可以參考下
    2018-06-06

最新評(píng)論

营口市| 中方县| 陆川县| 鸡东县| 青铜峡市| 大方县| 年辖:市辖区| 柏乡县| 博罗县| 尼木县| 大足县| 工布江达县| 西华县| 万州区| 花垣县| 安化县| 东明县| 武穴市| 永安市| 日照市| 合肥市| 郑州市| 富锦市| 灯塔市| 夏河县| 金昌市| 泗水县| 崇文区| 华阴市| 通许县| 彰化县| 萨迦县| 扶绥县| 咸宁市| 凉城县| 玉屏| 那曲县| 泗洪县| 青田县| 晋城| 藁城市|