京东评价晒单系统的组件化设计

来这里找志同道合的小伙伴!

作者:王新栋 目前就职于京东,一直从事京麦平台的架构设计与开发工作,熟悉各种开源软件架构。在web开发,架构优化上有较丰富实战经历。有多年在NIO领域的设计、开发经验,对HTTP、TCP长连接技术有深入研究与领悟,目前主要致力于移动与PC平台网关技术的优化与实现。

写在前面

用户在电商网站上形成购买决策,通常需要综合考虑很多信息,如商品的外观、价格、售后服务等。购买过该商品的用户对商品的打分、评论和图片分享等内容,也是帮助用户形成购买决策的重要参考。京东的评价晒单系统就是将用户购物后的评价发表、购物时的评价展示参考等功能结合起来的一整套解决方案。本文通过对京东评价晒单系统的技术架构和日常工作范畴进行介绍,引申出评价晒单系统在组件化方面的设计理念与方案,希望可以让读者对京东的评价晒单系统有一个全面的了解。

评价晒单系统的技术架构介绍

技术方案与架构

目前京东支持多种维度的评价内容,包括:

》商品评分(可以打1~5分)。

》文字评论(评论内容10字以上,并且商品价格大于一定金额可以获赠京豆)。

》用户拍摄与商品相关的图片或视频上传分享(以下称为晒单)。

》服务评价,包括物流服务、安装服务、汽车门店服务等,可以针对不同服务的指标(如送货速度)进行打分。

在评价内容的展示上,用户可以在个人中心里看到自己已经发表过的评价内容,以及购买后尚未评价的商品,可以从个人中心的入口进入发表评价;在商品信息的展示页,用户可以看到针对商品的评价列表以及不同评分下的评价数量(好、中、差评数),还可以只看晒单内容;所有的评价内容(包括服务评价)都可以在后台页面进行查询,以便审核人员审核内容,以及供采销人员查看商品的用户反馈情况等。

评价晒单系统主要解决的就是用户的数据存储和查询的问题。下图展示了京东评价晒单系统的架构图:

评价晒单系统整体架构图

架构图中间上部的“评价中间件”模块用来提供各个终端(如PC、APP、M页、微信、手机qq等)和其他业务部门需要的接口,主要包括数据写和读两类接口。由于评价晒单系统在存储上文提到的评价内容信息之外,其他与之关联的用户账户和订单号、商品号等信息,只存储关联的相关id信息,所以在评价中间件提供接口数据时,为了数据展示的需要,该模块需要查询其他服务的接口,补充用户信息(如头像、昵称)或者商品信息(商品图片、描述等)等数据的下发。

评价中间件存储和读取用户发布的评价内容,是通过调用“评价基础服务”模块提供的接口来与数据库进行解耦。评价基础服务,提供了MySQL、MongoDB、HBase三种数据存储方式。MySQL用来存储用户账户和发布的评价内容的对应关系表,以及评价内容和商品编号的对应关系表,评价回复之间的回复关系表等关系信息;MongoDB和HBase用来存储评价的文字和图片视频地址(仅存储地址链接,不存储媒体内容)信息等内容,两者互相备份。用户发布评价内容调用评价中间件的接口后,一方面将评价数据通过评价基础服务存在数据库里,另一方面由评价中间件发出消息,架构图左右两侧的“前台搜索服务”和“后台搜索服务”分别订阅这个消息,获得评价内容发布的新增消息。这时两个搜索服务模块,会将新增的评价内容写入Solr服务器。

Solr是企业级的搜索应用服务器,其中前台搜索服务和后台搜索服务按照不同的分片规则和数据字段需求,写入评价内容到Solr服务器后,就可以支持各种业务的查询需求。前台搜索服务会将查询最频繁的数据在Solr搜索出来后,存入Redis缓存服务,以便缓解Solr服务器的查询压力。评价中间件的读接口请求,也会先查询Redis获取缓存数据,减少访问评价基础服务和数据库的压力。

架构图右下侧的“评价管理后台”供审核或采销人员直接查询Solr服务器,在后台页面上维护线上的评价晒单数据的展示。“评价后台任务”通过对接订单完成消息,更新用户的评价资格数据并进行评价完成后奖励京豆的发放。

当前系统的优势与挑战

评价晒单系统与社区类网站有一定的相似性,支持用户发布文字和图片内容,以及互相评论等功能,但是京东的评价晒单系统与交易等业务深度绑定,需要记录交易、商品等维度的对应关系。因此为了更好的适合公司的业务开发,我们没有采用一些现有的社区开源框架进行改造,而是独立设计了上述系统。

当前系统做到了模块之间的解耦,新发布的内容及时记录到增量日志中,由后续的任务异步消费和更新相关缓存;模块之前通过消息订阅的方式通知数据的新增与修改;Redis缓存满足了大流量的查询请求,因此在应对高并发的数据读写请求上,有较好的抗压能力;对Solr的使用也满足了查询的可扩展性与性能,在业务支持上也有一定的便捷性。

当前系统的挑战主要来自数据的快速增长对存储资源的消耗和性能影响。一方面在数据库以及Solr中需要存储全部评价内容,以便满足不同维度的查询和展示需求,另一方面大量的数据会拖慢查询的效率,因此对数据进行合理的划分管理,并且实现弹性的数据扩容方案,是系统架构优化的方向。日常的工作还有很多创新性的业务开发,在功能不断增加的过程中,保持系统的模块与功能清晰划分,部分业务进行组件抽离,也是一项很有挑战的工作。

日常工作范畴

在对评价晒单系统的日常维护开发过程中,主要有如下一些工作内容:

数据整理任务

用户发布的评价文字和图片内容鱼龙混杂,我们会定期对存量内容进行语义方面的扫描,挖掘出高质量的评价内容,提高其在列表中的排序位置,也会对一些无意义的内容进行沉底或者折叠标记,以便节省用户浏览的时间。评价晒单系统通过接口的形式调用评价内容语义评分接口,语义质量评判由专业的算法团队对数据进行深度学习来实现。

数据获取条件的变更

为了让用户在查看商品信息时快速浏览到最有价值的评价内容,评价列表进行了多种形式的展现,比如可以分别查看好、中、差评以及只看晒单图片等。有一些商品的评价内容需要对评价的发表时间做过滤,比如只展示最近三个月的内容,以便卖家在更新服务质量后,可以通过评价得到体现。还可以根据商品之间的绑定关系,在一个商品下面绑定其他商品的评价信息一起展示,以便给用户更多更好的参考信息。这些工作要通过在查询Solr生成缓存时,增加或者修改查询条件,支持新的列表产生,同时在中间件接口中也涉及到一些逻辑的改动工作。

新字段的引入与融合

由于对接的业务和功能越来越多,原有评价内容的存储字段会需要扩展,比如视频晒单的引入就需要增加一个媒体类型字段。新字段在增加时会考虑未来的可扩展性,尽量能包含较广的含义,避免频繁增加字段。在查询展示时根据新字段进行特殊逻辑的处理,以便支持新的业务功能。由于评价晒单系统的模块较多,新字段加入通常对各模块都有影响,因此需要额外注意整体的联调和数据一致性。

对接新业务,展示新内容

为了满足用户对商品评价更全面多维的了解,除了展示评价数量、好评度、评价列表等内容,我们也在借助AI和大数据的能力进行诸多扩展尝试。算法团队通过对历史评价数据进行挖掘分析,可以抽取评价内容中的语义标签,如“屏幕清晰度高”、“衣服尺码偏大”等短语,同时对包含该短语或者含义与之相关的内容进行聚类,而后以接口的形式给评价晒单系统获取商品评价下面的语义标签和每个标签对应的评价列表。

另一方面,除了给用户展示评价内容,还需要将评价发布者的头像、等级等信息进行展示,比如对京东Plus会员发布者进行特殊标记的展示、将发布者的京享值分数进行展示等;在用户完成评价后,需要对接京豆发放系统给用户发放京豆,这里也会对接新的业务:如京享值等系统的积分变更;还有一些创新的业务,需要使用用户发布的评价晒单内容,在用户发布内容时,评价晒单系统会同步数据给新的业务方,并对接业务方的运营后台消息,及时标记新业务使用到的数据状态,以便在数据下发时进行区分展示。

这些工作通常对现有系统的改造较大,很多工作属于从0到1的开发,会占用大部分的研发工时。

异常处理与数据治理

我们有单独的反馈渠道,可以响应客服那边的需求,比如处理一些商家回复数据的展示问题和用户内容审核的错误。在评价晒单系统中,有若干修复工具,可以实现对单个商品或者某个用户下面评价晒单数据的重新计算与更新,以便解决多个模块同步数据过程中极少出现的数据不一致问题。

由于京东自身业务与用户量的快速增长,在数据存储上,评价晒单系统的存储容量也一直面临挑战,日常工作中对于容量即将饱和的数据库进行扩容,以及及时清理和缩减一些不必要的数据,也是重要的工作内容之一。

评价晒单系统的组件化设计

伴随着京东未来的发展战略,以及国际站项目的落地,评价晒单系统也需要从单一业务做到多元业务的支持,从单一的数据源做到多套数据源,实现系统的快速复制部署,以便达成业务的横向扩展和纵向创新。为了这一目标,我们的系统既要有小而美的灵巧,又要有大而全的能力,在应对这样的组件化系统要求上,我们采用了如下的设计方案:

系统的小而美

由于以往业务快速发展的需要,目前的评价晒单系统在数据层面并没有完成很好的分层设计,因此在数据库切换时,会涉及到对多个模块的影响,切换成本较高。针对这些问题,在进行国际站的开发过程中,我们对评价晒单系统进行了更合理的模块数据分层设计。主要包括:

管理对数据资源的使用

评价晒单系统包含中间件、基础服务、前台后台搜索、管理后台等模块,这些模块在数据资源的使用上存在着很多交集。为了减少数据资源变更的影响,我们把对MySQL、MongoDB和HBase数据库的读写操作,都收归到基础服务模块中。基础服务模块最终以接口的形式给其他模块调用,实现对数据库的访问。开发人员可以定义自己对数据库的使用接口,由基础模块开发人员完成,这样就节省了其他模块对数据库的访问配置操作,在数据库变更时也仅仅需要修改基础服务一个模块。

Redis和Solr涉及到的模块较少,而且查询逻辑和业务耦合性较高,因此在各模块内部进行数据分层管理,直接访问这些资源。对Redis和Solr进行合理的分组与分片规划,以便管理。分组可以将业务含义相关的数据在同组存储,在日常维护中可以仅对有问题的分组进行切换,分片可以对单组的数据进行容量和性能扩展,满足数据量的快速增长。

业务逻辑和存储资源的插拔设计

组件化要考虑的问题之一是系统的可迁移性与可复制性,在进行国际站的开发过程中,我们对原有系统进行了业务流程的精简改造,实现了仅包括文字、图片评价的最小化评价晒单系统功能开发。这套最小化功能系统,可以理解为评价晒单系统的内核,通过将数据库资源管理收归基础模块,Redis和Solr采用配置文件进行分组分片的配置管理,在需要部署新的系统时,只需要配置好新的数据资源,就可以使用内核功能。对于不同业务或者地区需要的特殊逻辑功能,在中间件模块进行定制开发,独立部署,实现新系统的快速部署上线。

接口的调用和部署方式

评价晒单系统以接口的形式对外提供的服务,接口传递的数据来自于上文提到的数据存储资源配置。接口的使用方,包括了使用不同数据资源的业务部门,也包括了使用相同数据资源的不同终端设备。为了便于管理,在中间件接口逻辑的开发上,会采用一套代码,部署多个中间件分组的形式,支持不同的接口使用方。没有特殊逻辑的接口在各个分组中都可以调用,数据来自不同分组连接的不同基础服务模块分组;有的分组需要特殊逻辑的接口,则在这个分组下面开通这个接口的访问权限,其他不需要此接口的分组可以禁止接口的调用。基础服务模块也用同一套代码部署不同的分组,每个分组对应独立的数据资源,有几个数据资源,就建立几个分组。不同的中间件分组可以配置不同的基础服务模块分组,从而满足业务和数据源的多样性需求。

评价晒单系统组件化的部署方式示意图

系统的大而全

国际站使用评价晒单系统的核心功能,通过可插拔的数据资源配置方式,实现了小而美的架构方案。国内方面,经过多年的功能创新和业务发展,已经形成了庞杂而繁复的业务逻辑与海量的业务数据,在功能扩展和组件化抽象方面也有很多挑战。为了应对不同业务对国内系统的定制需求,我们也做了如下工作:

合理区分数据来源

上文提到评价晒单系统的不同模块和数据库可以进行分组部署,在同一个数据库内,还需要对数据进行来源的标记,比如区分数据来源于哪个特殊业务(如充值、二手、1号店等),数据来源于中间件的PC端还是App端,评价数据是文字、图片还是视频等信息。这些数据来源与格式的标记信息,作为独立字段记录了数据的身份信息,之后混合存储在同样的数据格式中,而不是分开存储,以便于数据的统一维护与管理。在中间件提供的接口需要对数据进行区分获取时,根据逻辑的复杂性,简单的过滤逻辑可以在基础服务模块获取数据时添加,复杂的过滤逻辑由中间件自行区分下发,从而实现了大而全的数据融合存储方案。

控制数据的产生和展示规则

上文提到对同一数据库中不同来源的评价数据采用统一的存储方案,来源复杂的数据需要严格控制数据产生时入库的条件,并且在展示时定制不同的规则。

目前的评价晒单系统需要在用户完成订单后,才可以对订单中的商品进行评价,并且有评价的时效要求(超过X天无法评价)。评价晒单系统通过消息的形式订阅交易系统的订单完成消息,收到该消息后,可以设置不同的规则,比如根据订单类型、订单来源等条件,过滤出可以产生评价资格的用户与商品对应关系,得到评价凭证存入数据库。也可以设置不同的凭证类型,针对订单或者商品的种类,在凭证产生时,区分不同的评价资格,比如有的品类的商品没有服务评价资格,在订单完成时就记录了凭证的类型。这部分也可以抽离出来,做成评价凭证管理中心,针对不同的分组,配置不同的凭证产生条件与凭证类型,从而实现灵活的评价资格管理。

对混合数据的展示上,总体上分为两个维度,一是与商品关联的对商品的所有评价数据,在用户浏览商品信息时进行展示,帮助用户形成购买决策;二是与用户关联的,当前用户发布过的评价历史等信息,帮助用户管理和查看自己的评价信息。前文在日常工作范畴中的“数据获取条件的变更”一节介绍过相关内容。值得再次说明的是,展示的数据并非都是通过中间件查询基础服务模块获得,特别是第一个维度和商品关联的数据,需要有Redis来缓存数据,从而减轻基础服务后方的数据库访问压力。缓存数据的来源于前台搜索服务模块对Solr指定不同的索引查询条件来获取的数据。

在缓存中设计简单可依赖的数据

为了保持数据的实时更新,即在新的评价内部发表后,其他用户可以尽快地浏览到最新评价,我们会将评价缓存列表实时更新。前台搜索模块收到最新的评价发布或者修改消息后,会将新的信息写入Solr服务器,然后触发列表缓存更新任务,按照指定的查询条件,从Solr中有序地取出需要的评价数据列表放入缓存,满足中间件的查询请求。列表缓存中只存储评价数据的id信息,具体内容到基础服务模块中通过NoSQL的批量查询来获得,这样一方面节省了缓存的容量,另一方面也便于具体内容的实时更新。

除了列表缓存,对于一些访问量较高的商品,其前N页的评价晒单数据需要全部进行缓存,以便避免大量的NoSQL批量查询打到基础服务模块及数据库上。我们使用了Guava Cache的本地缓存方案来折中对Redis资源的大量占用,取得了资源和性能的平衡。

复杂关系型数据的隔离管理

在评价晒单系统的主流程以外,还有很多小的功能,比如对评价内容点赞、举报、回复、追加评论等,这些数据不作为扩展字段存储在评价主数据中,而是通过id的对应关系单独存储在其他数据表中。这样就保证了主流程和核心数据的可控性,这些附加功能可以更加自由地与主流程进行组合与剥离。

管理后台与监控系统

基于以上的介绍,我们了解了评价晒单系统在大小的伸缩之间,如何满足业务的需求。为了保障数据的安全可控,评价晒单系统具有功能复杂的管理后台可以实现对用户发布内容的审核与推荐等操作,同时有一套完备的业务和资源监控系统来保证服务的稳定可靠。

评价管理后台查询功能示意图

管理后台支持各种维度的查询检索,方便审核人员快速查找评价内容并进行相应操作。管理后台直接查询后台搜索服务维护的Solr服务器,在Solr服务器中存储完整的评价相关字段内容,以便支持各种查询条件。后台搜索服务维护的Solr服务器,采用按照时间分片的方式管理数据,通过指定查询数据的时间范围,节省不分片时在全部数据中搜索的性能代价。在应对系统的自我复制和功能扩展方面,可以通过配置不同Solr服务器的资源地址实现系统复制,通过消息传递管理后台的审核信息,实现模块间的依赖解耦;在前端页面和查询条件层分别进行新的查询维度添加与扩展,也可以快速地支持新业务的管理功能。

监控系统包括对数据库和缓存资源的使用量、查询性能等维度的监控,也有对系统服务器稳定性和系统使用方调用量的监控,还有代码维度的异常统计与监控。每个维度的监控都可以设置达到一定阈值的报警规则,以便开发人员及时发现和处理线上问题。

写在最后

评价晒单系统在应对数据快速增长、业务不断创新、系统日趋复杂的挑战过程中,通过低耦合的模块依赖关系、异步的计算任务调度以及完善的监控管理系统,来保障业务功能的不断升级。未来在系统功能上,我们会在核心功能以外,抽象更多的组件和功能,先通过接口层的分离实现定制化的功能输出,再将底层数据系统进行更好的逻辑划分,从而帮助公司的各项业务更快更好地使用评价晒单系统的丰富功能。

原文发布于微信公众号 - 京东技术(jingdongjishu)

原文发表时间:2018-06-01

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏喵了个咪的博客空间

IOT设备通讯协议MQTT

哈喽大家好呀!笔者的公司最近在做IOT设备相关的业务,基于这个契机寻找学习了一下关于IOT通讯协议相关的内容,最终在技术选型上选择了使用MQTT协议并且结合EM...

2694
来自专栏灯塔大数据

如何打造高性能大数据分析平台

大数据分析系统作为一个关键性的系统在各个公司迅速崛起,但是这种海量规模的数据带来了前所未有的性能挑战。同时,如果大数据分析系统无法在第一时间为运营决策提供关键数...

3459
来自专栏腾讯移动品质中心TMQ的专栏

探索式测试基础系列——生活协奏曲

前文讲过,探索式测试能为平常的生活带来浪漫因子,在浪漫一段时间后,新奇感消失,但效果仍在,探索式测试与日常测试真正融为一体,深刻作用于产品质量保证,共同演奏出...

18810
来自专栏Spark学习技巧

浪院长 | spark streaming的使用心得

主要是转换算子,action,和状态算子,这些其实,就按照api手册或者源码里接口介绍结合业务来编码。

1362
来自专栏斑斓

选择缓解风险的技术

三. 选择缓解风险的技术 一旦识别出迁移过程中可能存在的风险,我们就可以有的放矢地选择相关技术,制订降低风险的解决方案。 寻找丢失的知识 只有体验过去,才能谋...

3419
来自专栏CSDN技术头条

如何打造高性能大数据分析平台

原文:Building High Performance Big Data Analytics Systems 译者:袁璞,圣特尔•E店宝大数据架构师,关注高性...

2287
来自专栏华章科技

如何打造高性能大数据分析平台

译者:袁璞,圣特尔•E店宝大数据架构师,关注高性能或可用架构、大数据技术、机器学习。

421
来自专栏ThoughtWorks

Web App性能优化之亮剑|洞见

自计算机诞生以来,系统性能问题亘古未变,从指令级优化到集成系统的优化,可谓愈来愈复杂。每种类型的性能问题即便出现的场景不尽相同,但依然有一些性能优化模式,久经沙...

3296
来自专栏Java帮帮-微信公众号-技术文章全总结

研究微信即时通讯的服务端、朋友圈、红包、推送等方案

即时通信:前端获得消息发送到服务端,服务端处理后通过推送的方式,给到接收方;Android使用长连机制,联通网络长连十几分钟,电信仅五六分钟,因此需要根据测试的...

2753
来自专栏华章科技

【译文】如何打造高性能大数据分析平台

大数据是最近IT界最常用的术语之一。然而对大数据的定义也不尽相同,所有已知的论点例如结构化的和非结构化、大规模的数据等等都不够完整。大数据系统通常被认为具有数据...

574

扫码关注云+社区