情景

后端使用微服务架构,和数据库交互的服务使用C++的BRPC编写,文件管理服务使用Python的web.py编写。在业务逻辑中,一个“资源”是由一个数据库项和一个文件来定义的。当删除一个"资源"时,需要同时删除数据库项和文件,这就涉及到跨语言微服务之间的调用问题。
后台管理系统请求删除某项资源时,先向BRPC发出请求。BRPC收到请求后,需要完成三个子逻辑:

  1. 从数据库中获取资源对应文件的URL
  2. 根据文件URL,调用Python编写的文件服务,删除该文件
  3. 删除该资源对应的数据库项

问题

当使用BRPC调用Python编写的服务时,无法解析出该服务返回的信息。比如,该服务返回{“code”:200},BRPC使用同样的pb结构接收该json,但无法解析出code=200的信息。

分析

在启动BRPC的Server的时候,传入-http_verbose=true,令http索引信息都打印在info中。可以看到BRPC和web.py交互的http如下:

[ HTTP REQUEST @127.0.0.1 ]^M
> POST /delete HTTP/1.1^M
> Content-Length: 31^M
> Host: 127.0.0.1:8082^M
> Content-Type: application/json^M
> Accept: */*^M
> User-Agent: brpc/1.0 curl/7.0^M
> ^M
{"path":"/bubble/\E8\B5\84\E6\BA\90 f.png"}
I0612 15:58:55.156672 18185 http_message.cpp:290]
[ HTTP RESPONSE @127.0.0.1 ]
< HTTP/1.1 200 OK
< Transfer-Encoding: chunked
< Date: Fri, 12 Jun 2020 07:58:55 GMT
< Server: localhost
<
{"code": 200, "msg": "OK"}
I0612 15:58:55.156754 18185 FileServiceClient.cc:36]
E0612 15:58:55.156760 18185 FileServiceClient.cc:39] fail to delete file.code=0.msg=
I0612 15:58:55.157089 18185 http_rpc_protocol.cpp:221]
[ HTTP RESPONSE @127.0.0.1 ]^M
> HTTP/1.0 200 OK^M
> Content-Length: 45^M
> Content-Type: application/json^M
> ^M
{"code":506,"msg":"call file_service error."}

可以发现,web.py返回的response的内容符合json格式,但其http头中的Content-Type并没有像BRPC给出的response一样标明是application/json。怀疑是因为web.py未标明为json格式,导致BRPC无法分辨出其为json,从而无法解析出该信息。

修复

在web.py对应方法中,加入

web.header('Content-Type','application/json')

问题得到修复

后记

使用BRPC访问其他使用http/h2提供的服务,需要服务提供方在http头标明格式为json/pb。

Logo

权威|前沿|技术|干货|国内首个API全生命周期开发者社区

更多推荐