热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

javametadata使用_如何在客户端使用Java读取gRPC中的元数据

我正在使用Java和Protoc3.0编译器,我的proto文件在下面提到.https:github.comopenconfigpublicblobmasterreleasemod

我正在使用

Java和Protoc 3.0编译器,我的proto文件在下面提到.

https://github.com/openconfig/public/blob/master/release/models/rpc/openconfig-rpc-api.yang

syntax = "proto3";

package Telemetry;

// Interface exported by Agent

service OpenConfigTelemetry {

// Request an inline subscription for data at the specified path.

// The device should send telemetry data back on the same

// connection as the subscription request.

rpc telemetrySubscribe(SubscriptionRequest) returns (stream OpenConfigData) {}

// Terminates and removes an exisiting telemetry subscription

rpc cancelTelemetrySubscription(CancelSubscriptionRequest) returns (CancelSubscriptionReply) {}

// Get the list of current telemetry subscriptions from the

// target. This command returns a list of existing subscriptions

// not including those that are established via configuration.

rpc getTelemetrySubscriptions(GetSubscriptionsRequest) returns (GetSubscriptionsReply) {}

// Get Telemetry Agent Operational States

rpc getTelemetryOperationalState(GetOperationalStateRequest) returns (GetOperationalStateReply) {}

// Return the set of data encodings supported by the device for

// telemetry data

rpc getDataEncodings(DataEncodingRequest) returns (DataEncodingReply) {}

}

// Message sent for a telemetry subscription request

message SubscriptionRequest {

// Data associated with a telemetry subscription

SubscriptionInput input = 1;

// List of data models paths and filters

// which are used in a telemetry operation.

repeated Path path_list = 2;

// The below configuration is not defined in Openconfig RPC.

// It is a proposed extension to configure additional

// subscription request features.

SubscriptionAdditionalConfig additional_config = 3;

}

// Data associated with a telemetry subscription

message SubscriptionInput {

// List of optional collector endpoints to send data for

// this subscription.

// If no collector destinations are specified, the collector

// destination is assumed to be the requester on the rpc channel.

repeated Collector collector_list = 1;

}

// Collector endpoints to send data specified as an ip+port combination.

message Collector {

// IP address of collector endpoint

string address = 1;

// Transport protocol port number for the collector destination.

uint32 port = 2;

}

// Data model path

message Path {

// Data model path of interest

// Path specification for elements of OpenConfig data models

string path = 1;

// Regular expression to be used in filtering state leaves

string filter = 2;

// If this is set to true, the target device will only send

// updates to the collector upon a change in data value

bool suppress_unchanged = 3;

// Maximum time in ms the target device may go without sending

// a message to the collector. If this time expires with

// suppress-unchanged set, the target device must send an update

// message regardless if the data values have changed.

uint32 max_silent_interval = 4;

// Time in ms between collection and transmission of the

// specified data to the collector platform. The target device

// will sample the corresponding data (e.g,. a counter) and

// immediately send to the collector destination.

//

// If sample-frequency is set to 0, then the network device

// must emit an update upon every datum change.

uint32 sample_frequency = 5;

}

// Configure subscription request additional features.

message SubscriptionAdditionalConfig {

// limit the number of records sent in the stream

int32 limit_records = 1;

// limit the time the stream remains open

int32 limit_time_seconds = 2;

}

// Reply to inline subscription for data at the specified path is done in

// two-folds.

// 1. Reply data message sent out using out-of-band channel.

// 2. Telemetry data send back on the same connection as the

// subscription request.

// 1. Reply data message sent out using out-of-band channel.

message SubscriptionReply {

// Response message to a telemetry subscription creation or

// get request.

SubscriptionResponse response = 1;

// List of data models paths and filters

// which are used in a telemetry operation.

repeated Path path_list = 2;

}

// Response message to a telemetry subscription creation or get request.

message SubscriptionResponse {

// Unique id for the subscription on the device. This is

// generated by the device and returned in a subscription

// request or when listing existing subscriptions

uint32 subscription_id = 1;

}

// 2. Telemetry data send back on the same connection as the

// subscription request.

message OpenConfigData {

// router name:export IP address

string system_id = 1;

// line card / RE (slot number)

uint32 component_id = 2;

// PFE (if applicable)

uint32 sub_component_id = 3;

// Path specification for elements of OpenConfig data models

string path = 4;

// Sequence number, monotonically increasing for each

// system_id, component_id, sub_component_id + path.

uint64 sequence_number = 5;

// timestamp (milliseconds since epoch)

uint64 timestamp = 6;

// List of key-value pairs

repeated KeyValue kv = 7;

}

// Simple Key-value, where value could be one of scalar types

message KeyValue {

// Key

string key = 1;

// One of possible values

oneof value {

double double_value = 5;

int64 int_value = 6;

uint64 uint_value = 7;

sint64 sint_value = 8;

bool bool_value = 9;

string str_value = 10;

bytes bytes_value = 11;

}

}

// Message sent for a telemetry subscription cancellation request

message CancelSubscriptionRequest {

// Subscription identifier as returned by the device when

// subscription was requested

uint32 subscription_id = 1;

}

// Reply to telemetry subscription cancellation request

message CancelSubscriptionReply {

// Return code

ReturnCode code = 1;

// Return code string

string code_str = 2;

};

// Result of the operation

enum ReturnCode {

SUCCESS = 0;

NO_SUBSCRIPTION_ENTRY = 1;

UNKNOWN_ERROR = 2;

}

// Message sent for a telemetry get request

message GetSubscriptionsRequest {

// Subscription identifier as returned by the device when

// subscription was requested

// --- or ---

// 0xFFFFFFFF for all subscription identifiers

uint32 subscription_id = 1;

}

// Reply to telemetry subscription get request

message GetSubscriptionsReply {

// List of current telemetry subscriptions

repeated SubscriptionReply subscription_list = 1;

}

// Message sent for telemetry agent operational states request

message GetOperationalStateRequest {

// Per-subscription_id level operational state can be requested.

//

// Subscription identifier as returned by the device when

// subscription was requested

// --- or ---

// 0xFFFFFFFF for all subscription identifiers including agent-level

// operational stats

// --- or ---

// If subscription_id is not present then sent only agent-level

// operational stats

uint32 subscription_id = 1;

// Control verbosity of the output

VerbosityLevel verbosity = 2;

}

// Verbosity Level

enum VerbosityLevel {

DETAIL = 0;

TERSE = 1;

BRIEF = 2;

}

// Reply to telemetry agent operational states request

message GetOperationalStateReply {

// List of key-value pairs where

// key = operational state definition

// value = operational state value

repeated KeyValue kv = 1;

}

// Message sent for a data encoding request

message DataEncodingRequest {

}

// Reply to data encodings supported request

message DataEncodingReply {

repeated EncodingType encoding_list = 1;

}

// Encoding Type Supported

enum EncodingType {

UNDEFINED = 0;

XML = 1;

JSON_IETF = 2;

PROTO3 = 3;

}

为了进行服务调用(rpc TelemetrySubscribe),我首先需要读取具有订阅ID的头,然后开始阅读消息.现在,使用Java我能够连接服务,我确实介绍了拦截器但是当我打印/检索头时它是null.我的调用拦截器代码如下,

ClientInterceptor interceptor = new HeaderClientInterceptor();

originChannel = OkHttpChannelBuilder.forAddress(host, port)

.usePlaintext(true)

.build();

Channel channel = ClientInterceptors.intercept(originChannel, interceptor);

telemetryStub = OpenConfigTelemetryGrpc.newStub(channel);

这是读取元数据的拦截器代码.

@Override

public ClientCall interceptCall(MethodDescriptor method,

CallOptions callOptions, Channel next) {

return new SimpleForwardingClientCall(next.newCall(method, callOptions)) {

@Override

public void start(Listener responseListener, Metadata headers) {

super.start(new SimpleForwardingClientCallListener(responseListener) {

@Override

public void onHeaders(Metadata headers) {

Key CUSTOM_HEADER_KEY = Metadata.Key.of("responseKEY", Metadata.ASCII_STRING_MARSHALLER);

System.out.println("Contains Key?? "+headers.containsKey(CUSTOM_HEADER_KEY));

想知道有没有其他方法来读取元数据或第一个有订阅ID的消息?所有我需要阅读第一条有订阅ID的消息,并将相同的订阅ID返回给服务器以便流可以启动我使用相同的原型文件使用相同的Python代码,它通过下面的代码提供与服务器通信仅供参考:

sub_req = SubscribeRequestMsg("host",port)

data_itr = stub.telemetrySubscribe(sub_req, _TIMEOUT_SECONDS)

metadata = data_itr.initial_metadata()

if metadata[0][0] == "responseKey":

metainfo = metadata[0][1]

print metainfo

subreply = agent_pb2.SubscriptionReply()

subreply.SetInParent()

google.protobuf.text_format.Merge(metainfo, subreply)

if subreply.response.subscription_id:

SUB_ID = subreply.response.subscription_id

从上面的python代码我可以轻松检索元数据对象,不知道如何使用Java检索它?

在阅读metaData之后,我得到的是:元数据({content-type = [application / grpc],grpc-encoding = [identity],grpc-accept-encoding = [identity,deflate,gzip]})

但我知道从元数据到它还有一条线,也就是说

response {

subscription_id: 2

}

如何从Header中提取包含订阅ID的最后一个响应.我确实尝试了很多选项,我迷失在这里.



推荐阅读
  • Go Cobra命令行工具入门教程
    本文介绍了Go语言实现的命令行工具Cobra的基本概念、安装方法和入门实践。Cobra被广泛应用于各种项目中,如Kubernetes、Hugo和Github CLI等。通过使用Cobra,我们可以快速创建命令行工具,适用于写测试脚本和各种服务的Admin CLI。文章还通过一个简单的demo演示了Cobra的使用方法。 ... [详细]
  • 基于.NET Core框架nacos的简单应用
    什么是Nacos?服务(Service)是Nacos世界的一等公民。Nacos支持 ... [详细]
  • k8s入坑之路(14)scheduler调度 kubelet管理及健康检查
    kubelet主要功能Pod管理在kubernetes的设计中,最基本的管理单位是pod,而不是container。pod是kubernetes在容器上的一层封装,由一组运行在同一 ... [详细]
  • Skywalking系列博客1安装单机版 Skywalking的快速安装方法
    本文介绍了如何快速安装单机版的Skywalking,包括下载、环境需求和端口检查等步骤。同时提供了百度盘下载地址和查询端口是否被占用的命令。 ... [详细]
  • 使用在线工具jsonschema2pojo根据json生成java对象
    本文介绍了使用在线工具jsonschema2pojo根据json生成java对象的方法。通过该工具,用户只需将json字符串复制到输入框中,即可自动将其转换成java对象。该工具还能解析列表式的json数据,并将嵌套在内层的对象也解析出来。本文以请求github的api为例,展示了使用该工具的步骤和效果。 ... [详细]
  • Linux如何安装Mongodb的详细步骤和注意事项
    本文介绍了Linux如何安装Mongodb的详细步骤和注意事项,同时介绍了Mongodb的特点和优势。Mongodb是一个开源的数据库,适用于各种规模的企业和各类应用程序。它具有灵活的数据模式和高性能的数据读写操作,能够提高企业的敏捷性和可扩展性。文章还提供了Mongodb的下载安装包地址。 ... [详细]
  • Imtryingtofigureoutawaytogeneratetorrentfilesfromabucket,usingtheAWSSDKforGo.我正 ... [详细]
  • 解决nginx启动报错epoll_wait() reported that client prematurely closed connection的方法
    本文介绍了解决nginx启动报错epoll_wait() reported that client prematurely closed connection的方法,包括检查location配置是否正确、pass_proxy是否需要加“/”等。同时,还介绍了修改nginx的error.log日志级别为debug,以便查看详细日志信息。 ... [详细]
  • 本文记录了在vue cli 3.x中移除console的一些采坑经验,通过使用uglifyjs-webpack-plugin插件,在vue.config.js中进行相关配置,包括设置minimizer、UglifyJsPlugin和compress等参数,最终成功移除了console。同时,还包括了一些可能出现的报错情况和解决方法。 ... [详细]
  • Servlet多用户登录时HttpSession会话信息覆盖问题的解决方案
    本文讨论了在Servlet多用户登录时可能出现的HttpSession会话信息覆盖问题,并提供了解决方案。通过分析JSESSIONID的作用机制和编码方式,我们可以得出每个HttpSession对象都是通过客户端发送的唯一JSESSIONID来识别的,因此无需担心会话信息被覆盖的问题。需要注意的是,本文讨论的是多个客户端级别上的多用户登录,而非同一个浏览器级别上的多用户登录。 ... [详细]
  • Python已成为全球最受欢迎的编程语言之一,然而Python程序的安全运行存在一定的风险。本文介绍了Python程序安全运行需要满足的三个条件,即系统路径上的每个条目都处于安全的位置、"主脚本"所在的目录始终位于系统路径中、若python命令使用-c和-m选项,调用程序的目录也必须是安全的。同时,文章还提出了一些预防措施,如避免将下载文件夹作为当前工作目录、使用pip所在路径而不是直接使用python命令等。对于初学Python的读者来说,这些内容将有所帮助。 ... [详细]
  • 其实之前也有下载过完整的android源码,但是从来没有对这个做过一些总结,在加上最近需要经常去看,索性就在从新下载,编译一下,其实这些东西官网上面都有。http:sou ... [详细]
  • 阿里云监控URL的配置笔记
    篇首语:本文由编程笔记#小编为大家整理,主要介绍了阿里云监控URL的配置笔记相关的知识,希望对你有一定的参考价值。有很多细节需要记录 ... [详细]
  • 不同优化算法的比较分析及实验验证
    本文介绍了神经网络优化中常用的优化方法,包括学习率调整和梯度估计修正,并通过实验验证了不同优化算法的效果。实验结果表明,Adam算法在综合考虑学习率调整和梯度估计修正方面表现较好。该研究对于优化神经网络的训练过程具有指导意义。 ... [详细]
  • 在重复造轮子的情况下用ProxyServlet反向代理来减少工作量
    像不少公司内部不同团队都会自己研发自己工具产品,当各个产品逐渐成熟,到达了一定的发展瓶颈,同时每个产品都有着自己的入口,用户 ... [详细]
author-avatar
sense宏江
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有