忘记密码   免费注册 查看新帖 |

ChinaUnix.net

  平台 论坛 博客 文库 频道自动化运维 虚拟化 储存备份 C/C++ PHP MySQL 嵌入式 Linux系统
12下一页
最近访问板块 发新帖
查看: 25417 | 回复: 10

【好书推荐】微服务与单一服务架构的拼杀,如何选? [复制链接]

论坛徽章:
138
2015年亚洲杯之日本
日期:2015-04-28 13:32:012015年亚洲杯之朝鲜
日期:2015-05-06 10:16:442015年亚洲杯之日本
日期:2015-05-06 10:21:342015年亚洲杯纪念徽章
日期:2015-05-13 17:16:442015亚冠之北京国安
日期:2015-05-13 17:18:292015亚冠之鹿岛鹿角
日期:2015-05-13 17:19:062015亚冠之德黑兰石油
日期:2015-05-27 16:47:402015亚冠之塔什干棉农
日期:2015-05-28 15:24:122015亚冠之卡尔希纳萨夫
日期:2015-06-01 13:52:392015亚冠之柏斯波利斯
日期:2015-06-04 17:37:292015亚冠之阿尔纳斯尔
日期:2015-06-16 11:31:202015亚冠之塔什干火车头
日期:2015-06-23 10:12:33
发表于 2018-07-04 16:14 |显示全部楼层
话题背景:
微服务在过去几年成为一个非常受欢迎的话题。
v2-952cedacded73193857ff11d742a92b5_hd.jpg
“微服务狂热”就像这样:
Netflix在devops上非常棒。 Netfix做微服务。 所以:如果我做微服务,我也就非常擅长devops了。

很多情况下,团队已经付出了巨大的努力来选用微服务模式,却在选用之前并没有清楚应用于当前具体问题的成本和收益。
本篇话题的目的在于详细描述微服务是什么,为什么这种模式非常吸引人,还有一些目前遇到的关键挑战等问题。

讨论问题:
1. 如何理解微服务,简要说明您所理解的微服务是什么?
2. 与传统单一服务架构相比,在实战环境下,各自的优劣都有哪些?
3. 如果您考虑部署微服务,在业务部署过程中会遇到哪些关键挑战?

活动时间:2018年7月4日-8月4日

活动奖励:
活动结束后,我们将会选取5个讨论精彩的同学,送技术图书《Spring Cloud 微服务架构开发实战(全新升级版)》一本。
QQ截图20180704160346.jpg

出版社: 北京大学出版社
ISBN:9787301294567
版次:1
商品编码:12382428
包装:平装
开本:16开
出版时间:2018-06-01

购书链接:https://item.jd.com/12382428.html

内容简介:本书与其他书籍不同,特色是真正从实战角度出发,运用 Spring Cloud 技术来构建一个完整的微服务架构的系统。本书全面介绍 Spring Cloud 的概念、产生的背景,以及围绕 Spring Cloud 在开发微服务架构系统过程中所面临的问题时应当考虑的设计原则和解决方案。特别是在设计微服务架构系统时所面临的系统分层、服务测试、服务拆分、服务通信、服务注册、服务发现、服务消费、集中配置、日志管理、容器部署、安全防护、自动扩展等方面,给出了作者自己独特的见解。本书不仅介绍了微服务架构系统的原理、基础理论,还以一个真实的天气预报系统实例为主线,集成市面上主流的新的实现技术框架,手把手地教读者如何来应用这些技术,创建一个完整的微服务架构系统。这样读者可以理论联系实践,从而让 Spring Cloud 真正地落地。


样章试读: spring cloud微服务架构开发实战-试读.pdf (2.66 MB, 下载次数: 34)

论坛徽章:
6
未羊
日期:2013-11-15 09:12:28狮子座
日期:2013-12-10 10:10:54技术图书徽章
日期:2014-01-09 17:41:45技术图书徽章
日期:2014-01-09 17:42:04技术图书徽章
日期:2014-01-09 17:42:5215-16赛季CBA联赛之广夏
日期:2018-01-10 15:17:38
发表于 2018-07-07 16:46 |显示全部楼层
1. 如何理解微服务,简要说明您所理解的微服务是什么?

微服务,这个词语其实是第一次听说,我search了下定义,然后恍然明白,其实所谓的微服务,用更通俗接地气的词语来定义和描述的话,就是敏捷+模块的服务架构体系,如何解释敏捷,原来的亚马逊 CEO Bezos提出来的2 pizza就是微服务系统架构的鼻祖,2 pizza意思就是所有参与人从设计、开发、测试、运维所有人加起来 只需要2个披萨就够了(应用自网上资料),所以你能知道,既然要求敏捷,那要快并且高效,就要有模块化的思维方式,在汽车行业,如今大众,丰田都提倡模块化造成体系,不仅高效,而且很多可移植,在IT行业,这种模块化的思路也是,不仅代码可移植,如同乐高积木进行横向功能叠加,而且基于模块化的微服务,在运维方面,也是自成体系,不仅能减少模块的测试压力和成本,最后我认为这个微服务还是符合当下资源高效利用的政策的,很多系统逐渐从大而全变成小而精,对于开发,运维等等也是如此,微服务就非常符合这个命题。


2. 与传统单一服务架构相比,在实战环境下,各自的优劣都有哪些?
我认为存在即合理,没有所谓哪个好,只有哪个更合适,或者在当下需求和长期规划下,在不同阶段,何种架构更性价比高,对于单一架构体系,我认为复杂性高,接口冗余,稳定性中等是其特征,你可以说这是缺点,但是我认为对于比如大型金融架构,比如我所在的行业,这种soa的架构体系是主流,单一服务架构优势在于下属模块的差异度比较少,品类单一,规划比较完整,属于有了宏观架构和愿景进行搭建的方式,而微服务更适合互联网行业,快速部署,已经对于新技术的欢迎和迭代,是微服务的最佳实践场所



3. 如果您考虑部署微服务,在业务部署过程中会遇到哪些关键挑战?

主要是在金融行业,如果在已有的单一架构系统体系中,采用微服务的部署方式,与原来系统的耦合以及接口是要好好考虑的,要不然会出现四不像,既没有了原来大型单一系统架构的优势,微服务的快速,高效和低成本也会体现不出其最好的效果,还有就是我认为即使是模块化的微服务部署,在能力范围之内要选择好不同模块的耦合和类型选择,否则百花齐开虽然漂亮,但是纵向升级以及进行整合还是非常让开发和运维的人绞尽脑汁的。

论坛徽章:
1
2017金鸡报晓
日期:2017-01-10 15:13:29
发表于 2018-07-07 17:22 |显示全部楼层

1. 如何理解微服务,简要说明您所理解的微服务是什么?
微服务是一种架构风格,每个微服务仅专注于单一任务或功能。各个微服务可被独立部署,通过类似于Unix/Linux管道的松耦合的形式组成一个大型复杂软件应用。


2. 与传统单一服务架构相比,在实战环境下,各自的优劣都有哪些?
S/N对比点微服务架构单体架构结论
1上手难度API接口调用数据库共享或本地程序调用单体架构胜
2.1开发效率(简单项目)早期设计和沟通的工作量加大,随着项目规模和时间的推移,效率变化不大早期工作量小,随着项目规模和时间的推移,效率大幅度下降单体架构胜
2.2开发效率(复杂项目)早期设计和沟通的工作量加大,随着项目规模和时间的推移,效率变化不大早期工作量小,随着项目规模和时间的推移,效率大幅度下降微服务架构胜
3系统设计(高内聚低耦合)每个业务单独包装成一个微服务,数据和代码都从物理上隔离开来,实现高内聚低耦合相对容易以包的形式对代码进行模块划分,控制得当即可实现高内聚。但最终都是在数据层面将整个系统耦合在一起微服务架构胜
4系统设计(扩展性)独立开发新模块,通过API与现有模块交互在现有系统上修改,与现存业务逻辑高度耦合微服务架构胜
5需求变更响应速度各个微服务组件独立变更,容易实施敏捷开发方法需要了解整个系统才可以正确修改,容易导致不相关模块的意外失败微服务架构胜
6系统升级效率各个微服务组件独立升级,上手和开发效率高,影响面小需要了解整个系统才可以正确修改,容易导致不相关模块的意外失败微服务架构胜
7运维效率大系统被拆分为多个小系统,部署和运维难度加大,但可以利用DevOps等方式将运维工作自动化简单直接单体架构胜
8知识积累微服务组件可以在新项目中直接复用,包括前端页面一般以共享库的形式复用后台代码微服务架构胜
9.1硬件需求(简单项目)一个系统需部署多个微服务,需要启动多个运行容器整个系统只需要一个运行容器单体架构胜
9.2硬件需求(高要求项目)按需为不同业务模块伸缩资源节点为整个系统分配资源,导致冗余微服务架构胜
10.1项目成本(简单系统)项目早期和后期,成本变化曲线平缓项目早期成本低,后期成本大单体架构胜
10.2项目成本(复杂系统)项目早期和后期,成本变化曲线平缓项目早期成本低,后期成本大微服务架构胜
11非功能需求为单独的微服务按需调优,甚至更换实现方式和程序语言为整个系统调优,牵一发而动全身微服务架构胜
12职责、成就感拥有明确的职责划分,主人翁意识和成就感加强,容易形成自组织型团队职责不明确,容易产生扯皮行为微服务架构胜
13风险大系统被拆分为小系统,风险可被控制在小系统内,但也引入了各小系统之间的交互风险系统是一个整体,一荣俱荣,一损俱损微服务架构胜

3. 如果您考虑部署微服务,在业务部署过程中会遇到哪些关键挑战?
·运维开销及成本增加:整体应用可能只需部署至一小片应用服务区集群,而微服务架构可能变成需要构建/测试/部署/运行数十个独立的服务,并可能需要支持多种语言和环境。这导致一个整体式系统如果由20个微服务组成,可能需要40~60个进程。

·必须有坚实的DevOps开发运维一体化技能:开发人员需要熟知运维与投产环境,开发人员也需要掌握必要的数据存储技术如NoSQL,具有较强DevOps技能的人员比较稀缺,会带来招聘人才方面的挑战。

·隐式接口及接口匹配问题:把系统分为多个协作组件后会产生新的接口,这意味着简单的交叉变化可能需要改变许多组件,并需协调一起发布。在实际环境中,一个新品发布可能被迫同时发布大量服务,由于集成点的大量增加,微服务架构会有更高的发布风险。

·代码重复:某些底层功能需要被多个服务所用,为了避免将“同步耦合引入到系统中”,有时需要向不同服务添加一些代码,这就会导致代码重复。

·分布式系统的复杂性:作为一种分布式系统,微服务引入了复杂性和其他若干问题,例如网络延迟、容错性、消息序列化、不可靠的网络、异步机制、版本化、差异化的工作负载等,开发人员需要考虑以上的分布式系统问题。

·异步机制:微服务往往使用异步编程、消息与并行机制,如果应用存在跨微服务的事务性处理,其实现机制会变得复杂化。

·可测性的挑战:在动态环境下服务间的交互会产生非常微妙的行为,难以可视化及全面测试。经典微服务往往不太重视测试,更多的是通过监控发现生产环境的异常,进而快速回滚或采取其他必要的行动。但对于特别在意风险规避监管或投产环境错误会产生显著影响的场景下需要特别注意。


论坛徽章:
53
2015七夕节徽章
日期:2015-08-24 11:17:25ChinaUnix专家徽章
日期:2015-07-20 09:19:30每周论坛发贴之星
日期:2015-07-20 09:19:42ChinaUnix元老
日期:2015-07-20 11:04:38荣誉版主
日期:2015-07-20 11:05:19巳蛇
日期:2015-07-20 11:05:26CU十二周年纪念徽章
日期:2015-07-20 11:05:27IT运维版块每日发帖之星
日期:2015-07-20 11:05:34操作系统版块每日发帖之星
日期:2015-07-20 11:05:36程序设计版块每日发帖之星
日期:2015-07-20 11:05:40数据库技术版块每日发帖之星
日期:2015-07-20 11:05:432015年辞旧岁徽章
日期:2015-07-20 11:05:44
发表于 2018-07-08 17:06 |显示全部楼层
1. 如何理解微服务,简要说明您所理解的微服务是什么?
微服务架构是一项在云中部署应用和服务的新技术。大部分围绕微服务的争论都集中在容器或其他技术是否能很好的实施微服务,而红帽说API应该是重点。
微服务可以在“自己的程序”中运行,并通过“轻量级设备与HTTP型API进行沟通”。关键在于该服务可以在自己的程序中运行。通过这一点我们就可以将服务公开与微服务架构(在现有系统中分布一个API)区分开来。在服务公开中,许多服务都可以被内部独立进程所限制。如果其中任何一个服务需要增加某种功能,那么就必须缩小进程范围。在微服务架构中,只需要在特定的某种服务中增加所需功能,而不影响整体进程。
微服务不需要像普通服务那样成为一种独立的功能或者独立的资源。定义中称,微服务是需要与业务能力相匹配,这种说法完全正确。不幸的是,仍然意味着,如果能力模型粒度的设计是错误的,那么,我们就必须付出很多代价。如果你阅读了Fowler的整篇文章,你会发现,其中的指导建议是非常实用的。在决定将所有组件组合到一起时,开发人员需要非常确信这些组件都会有所改变,并且规模也会发生变化。服务粒度越粗,就越难以符合规定原则。服务粒度越细,就越能够灵活地降低变化和负载所带来的影响。然而,利弊之间的权衡过程是非常复杂的,我们要在配置和资金模型的基础上考虑到基础设施的成本问题。
微服务作为一项在云中部署应用和服务的新技术已成为当下最新的热门话题。但大部分围绕微服务的争论都集中在容器或其他技术是否能很好的实施微服务,而红帽说API应该是重点。
企业和服务提供商正在寻找更好的方法将应用程序部署在云环境中,微服务被认为是未来的方向。通过将应用和服务分解成更小的、松散耦合的组件,它们可以更加容易升级和扩展,理论上是这样。
微服务的基本思想在于考虑围绕着业务领域组件来创建应用,这些应用可独立地进行开发、管理和加速。在分散的组件中使用微服务云架构和平台,使部署、管理和服务功能交付变得更加简单。
微服务是利用组织的服务投资组合,然后基于业务领域功能分解它们,在看到服务投资组合之前,它还是一个业务领域。
微服务这一概念出现于2012年,是因软件作者Martin Fowler而流行,他承认这并没有精确地定义出这一架构形式,虽然围绕业务能力、自动化部署、终端智能以及语言和数据的分散控制有一些常见的特性。


2. 与传统单一服务架构相比,在实战环境下,各自的优劣都有哪些?

工作中使用了微服务架构,接下来的一段时间里,我会写一系列的文章来介绍微服务架构,同时我也会在github上写一个microservices的应用框架(地址会在后续文章给出)。


一、单一应用架构
1.上下文
你正在开发一个服务器端的企业级应用,它必须支持多种不同的客户端,包括桌面浏览器、手机浏览器、原生手机APP。这个应用也许还会暴露一个API,给第三方程序去调用。它也许还会与其他应用集成,通过web services或者一个消息代理。 这个应用通过运行业务逻辑、访问数据库、与别的系统交换消息、然后返回一个HTML/JSON/XML响应的方式来处理HTTP或者消息请求。对于这个应用的不同功能块, 有不同的逻辑组件与之对应。

2.问题与强制条件
问题: 这个应用的部署架构是怎样的?

强制条件:
  • 这个项目有一个开发者团队
  • 新的团队成员必须快速变得高效工作
  • 这个项目必须易于理解和修改
  • 你想要对这个项目实施持续部署
  • 你必须在多台机器上运行多个这个项目的复制品,从而达到期望的可伸缩性、可用性
  • 你想要利用新技术(框架、编程语言等)的优势

3.解决方案与例子

解决方案:

构建一个单一应用架构的应用,比如一个单一的Java War文件, 或者一个单一的Rails或者NodeJS代码的目录结构

例子:

假设你正在构建一个电子商务应用, 这个应用从客户那里收到订单,检验存货和客户的余额,然后发货。这个应用由多个组件构成,包括:前端UI,实现了用户接口; 以及一些后台服务,用来检查余额,维护存货和发货。

这个应用以一个单一应用架构部署, 比如是在Tomcat上运行的一个Java web应用。你可以在一个load balance后面运行多个应用实例,以达到提高可用性和可伸缩性的目的:





4. 这种解决方案的结果

这种解决方案有很多好处:

  • 易于开发:现在很多开发工具和IDE的目标都是支持开发单一应用结构的应用
  • 易于部署:你只要在合适的运行时环境上简单的部署一个WAR文件(或者目录结构)
  • 易于伸缩:你可以在一个load balance后面运行多个应用实例,以达到提高可用性和可伸缩性的目的

但是,一旦这个应用变得庞大,团队规模变大,这种解决方案的缺点变得越来越重大:

  • 巨大的单一应用结构的代码吓坏了开发者,尤其是团队里的新人。这个应用变得难以理解和维护。结果是,开发工作变得缓慢,而且,因为没有严格的模块界限,模块化常常会被打破。此外,因为很难去理解如何正确地实现一次变动,代码质量下降。

  • IDE负载严重:代码越多,IDE越慢,开发效率越低。

  • web容器负载严重: 项目越大,启动时间越长。这对于开发效率有很大影响,因为有很多时间都浪费在了等待web容器启动上面。这也影响了部署。

  • 持续部署很困难:一个庞大的单一应用架构的应用是频繁部署的障碍。为了更新一个组件,你需要重新部署一整个应用。这会中断后台的任务,比如Java里的Quartz job,这可能会导致问题。还有一种可能是,未更新的组件会在启动时失败,导致的结果是,重新部署的风险升高,不利于频繁更新。 这对UI开发者来说尤其是个问题,因为他们经常需要快速迭代和频繁的重新部署。

  • 伸缩这个项目变得困难:一个单一应用架构的应用只能在一个维度上伸缩。一反面,成交量上升时,可以通过运行更多实例的方法来伸缩,一些云服务甚至可以按需调节实例个数。但是在另一方面,这种架构难以根据数据量来调节。每个应用实例都会访问数据,使得缓存变得不那么有效,提高了内存消耗和I/O传输。同时,不同的组件有不同的资源需求,一个组件可能是CPU密集型,而另一个可能是内存密集型。单一应用架构下,我们很难对每个组件分别进行伸缩。

  • 对于调节开发规模是个障碍: 一旦一个单一应用架构的应用达到了一个具体的规模,把团队分别几个更小的团队,专注与不同的功能块上是有效的。比如说,我们也许想要UI团队、审计团队、仓储团队等。但是单一应用架构阻碍了各个团队之间的独立工作。团队之间必须共同合作。

  • 需要对一个技术栈有一个长期的承诺: 一个单一应用架构**你与一开始的技术栈捆绑(甚至与某一个技术的具体版本)。在单一应用架构下,很难增量应用新的技术。比如说,你选择了JVM技术,以后那些用非JVM语言写的组件在你的项目里就没有一席之地了。再比如,你选择了一个平台框架,后来这个框架过时了,那就很难去迁移到一个新的更好的框架了。很可能你为了采用新的框架,需要重写一整个应用,而这是很有风险的。




二、微服务架构


1.上下文
与上文单一应用架构相同

2.问题与强制条件
与上文单一应用架构相同



3.解决方案与例子
解决方案:
定义一个架构,使得这个应用的结构是一系列松耦合、互相合作的服务(services)。这个方法对应了伸缩立方体的Y轴。每个服务实现了一系列互相关联的功能。比如说,一个应用可能由订单管理服务、客户管理服务等构成。
服务之间用同步协议比如HTTP/REST或者异步协议比如AMQP(译者注: 实现如RabbitMQ等)来进行通信。 服务可以被独立的开发和部署。每个服务有自己独立的数据库,从而与别的服务解耦。服务之间的数据一致性通过使用事件驱动架构来维护。


例子:一个虚构的电子商务应用

假设你正在构建一个电子商务应用, 这个应用从客户那里收到订单,检验存货和客户的余额,然后发货。这个应用由多个组件构成,包括:前端UI,实现了用户接口; 以及一些后台服务,用来检查余额,维护存货和发货。这个应用由一系列服务构成:






4. 这种解决方案的结果

优点

这个解决方案有很多优点:

  • 每个微服务相对都比较小
    • 易于开发者理解
    • IDE更快
    • 应用启动更快,利于开发和部署
  • 每个服务可以独立于其他服务单独部署,利于频繁部署新版本

  • 更容易伸缩开发资源。使你可以把开发资源分成多个团队。每个团队负责一个或多个服务。

  • 提高了错误的隔离。比如说,在一个服务中产生了内容泄露,只有那一个服务会受影响。

  • 不会对一个技术栈产生长期的依赖。在开发一个新服务或者重写服务时,可以选择新的技术栈。

缺点
这个解决方案有很多缺点:


  • 开发者需要处理创建一个分布式系统时的额外的复杂度
    • 测试更复杂
    • 开发者必须实现服务间的通信机制
    • 如果不使用分布式事务,会很难实现跨多个服务的用例
    • 实现跨多个服务的用例需要团队间的更认真的合作
  • 部署复杂性。在生产环境下,部署或者管理一个微服务系统有运维方面的复杂性。
  • 更高的内存消耗。微服务架构需要N*M个实例,而单一架构只需要N个实例。如果每个服务在它自己的JVM上运行, 就需要M倍的JVM运行时。


5.问题
你有很多问题需要解决。

什么时候使用微服务架构?

使用这种方法的一个挑战是判断什么时候用它是有意义的。当开发一个应用的第一个版本时,你经常不会碰到这个方法所解决的问题。此外,使用一个精细的分布式的架构会拖慢开发进度。这对于一些初创公司来说可能是一个大问题,因为他们的挑战经常是如何快速的把业务模型实现到应用中。使用Y轴划分(译者注:这里应该指的是采用微服务架构)也许会使得快速迭代更难。但是过一段时间,当挑战变成了如何伸缩,以及你需要拆分功能块,这种紧密的依赖也许会使得拆分一个单一应用架构到一系列服务变得困难。


如何把应用拆解成多个服务?

另一个挑战是决定如何分离系统,成为一系列服务。这更像是一种艺术,但是也有很多策略可以帮到你:

  • 根据业务能力分离, 然后定义一个个服务
  • 根据子域来拆解
  • 根据用例/动词来拆解。比如说Shipping Service负责订单的输送。
  • 根据资源/名词来拆解。比如说,Account Service负责管理用户的账号。

理想情况下,每个服务应该只有一小部分的职责。(Uncle) Bob Martin 谈论过使用单一职责原则(SRP)来设计类,使用SRP来设计Service同样也是讲得通的。

另一个帮助设计Service的类比是Unix工具包的设计。Unix提供了很多工具,比如说grep, cat和find。每个工具只做一件事,然后可以和其他工具混合在一起,去做复杂的事情。


如何保持数据一致性?

为了保证松耦合,每个service有它自己的数据库。维护service之间的数据一致性是一个挑战,因为二阶段提交事务/分布式事务并不是很多应用的一个选项。相反的,一个应用必须使用事件驱动架构。一个服务在它的数据变化时,会发布一个事件。别的服务消费这个事件,然后更新自己的数据。有很多种可靠的数据更新和事件发布的方法,包括事件源事务日志跟踪


如何实现查询?

另一个挑战是实现需要从多个服务那里获取数据的查询。一个普遍的做法是使用命令查询职责分离,维护一个或多个view,它们通过订阅事件流的方式一直保持最新,事件流中的事件是别的service在数据变化时发布的。



3. 如果您考虑部署微服务,在业务部署过程中会遇到哪些关键挑战?

大家都在提微服务架构,微服务架构到底是什么?它有哪些特点和设计模式?我们在打造微服务架构过程中,这些设计模式在实战当中如何应用?数据的一致性应该如何保证?今天我将针对上述疑问分享一下我的思考。

微服务架构特点

什么是微服务架构?看下图的这段英文,这是Martin Fowler 在2014年提出来的,微服务架构是一种架构模式,既然是架构模式,那么,它就必然需要满足一些特点。他提到,微服务架构是一系列小的微服务构成的组合,那么,什么是“小的微服务”?可能每个人的理解都不一样,大家都应该都知道SOA架构,SOA架构的粒度是比较粗的,到底我们应该以什么样的粒度拆分微服务?我认为,微服务架构本质上一个业务架构,那么对业务了解的越深刻,你的微服务拆分就越合理。

比如我们做二手交易平台(转转),该平台包括用户体系、商品体系、交易体系以及搜索推荐体系。因为各个体系比较独立,那么我们就可以按照各个业务模块来拆分微服务。当然,这样做还不够,因为你的商品里面还有很多功能,但是大的思路是按照具体商品内部的逻辑来进一步拆分。

第二,围绕具体业务建模。一切脱离业务场景谈微服务架构都是耍流氓。
方法有二:首先将某一领域的模型作为独立的业务单元:比如二手交易中的商品、订单、用户等;其次将业务的行为作为独立的业务单元:比如发送邮件、单点登录验证、push服务。

第三,整个微服务都可以独立地部署,因为每一个维服务Process都是独立的,所以按照每个模块进行独立的部署也是很容易理解的。

第四,去中心化管理。打造去中心化管理意思就是微服务的每个模块和开发语言、运行平台没有关系,开发语言可以是C++,可以是go,也可以是世界上最好的语言,运行的平台是Linux,Unix、Windows等都可以。

最后一点就是轻量级通信,这点很容易理解,通信和模块语言、平台没有关系。尽可能选用轻量级的通信来做这个事情,这样实施跨平台、跨语言的时候就很容易。

讲完这些特点,我们可以看一看一个标准DEMO级的微服务架构到底是由哪些元素组成的?如下图,主要包括网关、微服务、数据存储、注册中心、配置中心。

既然是DEMO级的,和实际情况下相比肯定有所差别。那么,实际案例中,我们到底应该如何做这件事情?这个例子也是最近我在做的二手交易平台——转转。这里和DEMO有些不一样的地方。前面的第一层还是网关,下面有微服务的聚合层,作用是做各种业务逻辑的处理;聚合层下面是我们的数据原子层,主要做数据访问代理,只不过根据业务的不同垂直分开了。可以看到,网关、数据层,注册中心、配置中心都有,只不过在业务处理部分分成两层:一层是原子层,也就是整个数据访问的代理层,提供了用户的接口;另外一层就是上层的业务聚合层。

架构设计模式及实践案例

上面我大概讲了下微服务的一些特点以及DEMO级的微服务包括哪些部分以及实际案例中我们的设架构设计模式。那么,我们为什么要采用这种模式去做?除了这种架构模式之外还有哪些其它的架构模式?这里,模式还是非常多的,我会重点讲这几点:链式设计模式、聚合器设计模式和异步共享模式。

首先我们来说下链式设计模式,在这种模式下,APP前端请求首先要经过网关层,接下来连续调用两个微服务,调了微服务1之后还要调微服务2。为什么叫做链式呢?因为在调用过来以后先到微服务1,然后再同步地调用微服务2,微服务2会做一些处理,处理以后微服务2才会反馈给微服务1,微服务1再反馈给Gateway,最后反馈到APP。在实际业务场景中,涉及到交易和订单的业务场景都会用到这种模式。

接下来是聚合器设计模式,APP前端一个调用请求经过Gateway,到达聚合层,需要调用三个微服务,聚合层将三个微服务的返回结果做一些聚合处理,比如可以进行一些排序或者去重,聚合之后再反馈到Gateway和APP前端,这是一个典型的聚合器设计模式。

第三种模式是数据共享模式,这种模式相对比较简单,比如APP经过微服务网关,接下来调用微服务1和微服务2,理想情况下微服务1和微服务2都有自己独立的DB,但是有些情况下由于微服务1和微服务2的请求量和存储量较小,从资源利用率的角度来讲,这两个微服务的DB是共享的,因此这种就是数据的共享模式。

最后一种是异步消息设计模式,不管是链式设计、聚合器模式还是共享数据模式,架构模式都是同步模式。也就是说我的一个请求发出去必须等到每个环节都处理完才会给客户端。如果请求不需要关注处理结果,这时候可以异步来实施。APP更新请求经过微服务网关,持久化到MQ,写入MQ成功后马上Response给APP客户端,之后微服务根据需要从MQ里面订阅更新消息进行异步处理,我们为了提高吞吐量也会采用这种模式。

我从百度到转转这几年经历了很多业务场景,使用的无非就是聚合器、异步和数据共享的数据模式,特别是前面两个用得特别多,下面我们来看一些例子。

接下来我们看个例子,这是我们在2015年做的一个二手交易平台(转转),这个二手交易平台包括商品、分类搜索、关键词搜索、商品推荐等功能。一个用户请求过来,先经过网关,网关下面就是我们的聚合层,聚合层再去调用商品、交易、推荐以及搜索相关的,最终在聚合层把各个微服务原子层的结果汇总起来Response给到客户端。具体如下图所示:

异步消息模式的这个案例比较早了,当时我们做了Feed 流,类似现在的微信朋友圈,这是我在百度做的事情。当时,我们采用的架构模式是异步架构模式。前面是我们的APP,经过了网关,到达异步提交层,可以认为是持久化功能的MQ。用户请求经过网关到消息异步提交层后就返回了,业务处理部分从MQ里面读取数据再进行异步处理。这个时候吞吐量会增加,但是会带来一定的困惑。比如这个时候我发了一条Feed,用户再一查就直接到数据库里面查,可能异步提交消息队列有延迟,查不到,用户就困惑了,这个问题怎么解决?我们就想能不能在前端帮我们做一些事情?比如提交了MQ返回Response 200以后,前段配合插入这条Feed。用户再次刷新时候我相信已经是好几秒以后的事情了,即使有延迟,这个消息早就被你的业务处理完了。当然,我们这里是有特定场景的,社区时候可以这样去做,但是涉及到和金融相关的场景肯定不会这么去做。

数据一致性实践

微服务模块比较分散、数据也比较分散,整个系统复杂性非常高,如何进行数据一致性实践?在一个单体模块里面可以做Local Transaction,但是在微服务体系里面就不奏效。虽然难解决,但是不能不解决,不解决的话微服务架构就很难实施。我们知道微服务中做强一致性性的事情是非常难的,今天分享的更多的是解决最终一致性。因为在微服务下基于不同的数据库,Local Transaction是不可用的。大家在在分布式事务里面一定听说过两阶段提交和三阶段提交,这种场景其实在微服务架构里面也行不通,原因是因为它本质上是同步的模式,同步的模式之下做数据一致性吞吐量降低的非常多。

我们的业务场景无非是两种:第一种是异步调用,就是一个请求过来就写到消息队列里面就行,这种模式相对简单。今天主要讲下同步调用的场景之下怎么打造数据的最终一致性。既然是同步调用场景,并且不能降低业务系统的吞吐量,那么应该怎么做呢?建立一个异步的分布式事务,业务调用失败后,通过异步方式来补偿业务。我们的想法是能不能在整个业务逻辑层实现分布式事务语义策略?如何实现,无非有两种,第一是在调正常请求的时候要记录业务调用链(调用正常接口的完整参数),第二是异常时沿调用链反向补偿。

基于这个思路,我们架构设计上的关键点有三,第一是基于补偿机制,第二是记录调用链,第三是提供幂等补偿接口。架构层面,看下图,右边是聚合器架构设计模式,左边是异步补偿服务。

首先需要在聚合层引入一个Proxy。首先基于方法,在方法名加注解标注补偿方法名,比如:- @Compensable(cancelMethod=“cancelRecord”)

另外,聚合层在调用原子层之前,通过代理记录当前调用请求参数。如果业务正常,调用结束后,当前方法的调用记录存档或删除,如果业务异常,查询调用链回滚。

原子层我们做了哪些事情呢?主要是两方面,第一是提供正常的原子接口,其次是提供补偿幂等接口。

分布式事务关键是两个表(如上图),第一是事务组表,假设A->B->C三个请求是一个事务,首先针对ABC生成一个事务的ID,写在这个表里面,并且会记录这个事务的状态,默认的情况下正常的,执行失败以后我们再把状态由1(正常)变成2(异常);第二个表是事务调用组表,主要记录事务组内的每一次调用以及相关参数,所以调用原子层之前需要记录一下请求参数。如果失败的话我们需要把这个事务的状态由1变成2;第三,一旦状态从1变成2就执行补偿服务。这是我们的补偿逻辑,就是不断地扫描这个事务所处的表,比如一秒钟扫一次事务组表,看一看这个表里面有没有状态为2的,需要执行补偿的服务。这个思路对业务的侵入比较小。

具体看下我们实际的例子,比如二手交易平台里面创建订单事务组的正常流程,从锁库存到减红包再到创建订单,创建事务组完毕之后开始调用业务,首先Proxy记录锁库存调用的参数,之后开始锁库存服务调用,成功后之后又开始减红包和创建订单过程,如果都成功了直接返回。

再看一下异常的流程,前面几步都是一样的,只是在调红包服务、Proxy创建红包的时候如果失败了就会抛出异常,业务正常返回,聚合层Proxy需要把事务组的状态由1改成2,这个时候由左边的补偿服务异步地补偿调用。



论坛徽章:
30
CU大牛徽章
日期:2013-05-20 10:45:13数据库技术版块每日发帖之星
日期:2015-09-07 06:20:00每日论坛发贴之星
日期:2015-09-07 06:20:00每日论坛发贴之星
日期:2015-09-07 06:20:00数据库技术版块每日发帖之星
日期:2015-12-13 06:20:0015-16赛季CBA联赛之江苏
日期:2016-03-03 11:56:13IT运维版块每日发帖之星
日期:2016-03-06 06:20:00fulanqi
日期:2016-06-17 17:54:25IT运维版块每日发帖之星
日期:2016-07-23 06:20:0015-16赛季CBA联赛之佛山
日期:2016-08-11 18:06:41JAVA
日期:2016-10-25 16:09:072017金鸡报晓
日期:2017-01-10 15:13:29
发表于 2018-07-09 15:31 |显示全部楼层
1. 如何理解微服务,简要说明您所理解的微服务是什么?
微服务即Microservices,是一种软件架构模式和风格,以专注于单一责任和功能的小型功能块为基础,利用模组化的方式组合出复杂的大型应用程序,各功能块的使用与编程语言无关的API集相互通信。微服务架构运用于软件架构风格的其中一项概念是甘露运算(Dew Computing),意指由许多的“小露水”(即代表微服务的功能块)汇集而成的整体服务能力。微服务存在于一个更大的生态系统中。重要的是不要只考虑一个微服务。要确保微服务考虑如何连接到更大的系统中。
简而言之,微服务就是在业务逻辑上具备单一功能(或单项功能)的REST API服务。

2. 与传统单一服务架构相比,在实战环境下,各自的优劣都有哪些?
单体应用即Monolithic,单体应用架构即Monolithic Architecture。与微服务架构相比,

单体应用架构的优势:
1)易于开发(流行的IDE都适合)
2)易于测试(功能放于一起,部署于一个环境,测试方便)
3)易于部署(单体应用打包成一个WAR文件)
4)易于水平伸缩(通过负载均衡器,很容易增加或删除单体应用的节点)

单体应用架构的劣势:
1)维护成本的剧增
2)持续交付周期的剧增
3)新人培养周期长
4)技术选型成本高
5)可扩展性较差
6)构建全功能团队困难
7)随着业务规模的剧增,单体应用在架构上难以满足业务快速变化的需要
8)代码的可维护性、可扩展性、灵活性存在问题

3. 如果您考虑部署微服务,在业务部署过程中会遇到哪些关键挑战?
实施微服务架构,遇到的挑战会有很多,下面列举主要的挑战:
1)构建微服务架构有难度。微服务架构只是一种软件系统的架构风格,它不是国际标准,也没有硬性规则,很少有指导方针或文档可以帮助您了解如何使用微服务构建和部署软件。故要构建优秀的微服务架构,需要做大量的实践。
2)实施DevOps是一项挑战。微服务架构通常建立在云和虚拟化的基础之上,并且在很大程度上依赖于自动化来确保成功并避免故障。公司或组织应采用DevOps文化并拥有适当的基础架构以避免出错。
3)会打破现有的研发生态。应该知道,一旦打算开始微服务架构,切换回来就异常困难。必须在企业文化、工具和流程方面发生改变才能实现微服务。
4)开发微服务架构需要的技能比较高,部署、监控等都有一定的技术门槛。
5)微服务架构的日志管理也是一个挑战。
6)微服务架构的故障定位、故障隔离也是一个挑战。
6)对所有微服务实现版本管理和依赖管理也是一个挑战。

论坛徽章:
16
程序设计版块每日发帖之星
日期:2016-05-03 06:20:0015-16赛季CBA联赛之八一
日期:2018-07-05 10:34:0915-16赛季CBA联赛之八一
日期:2018-07-03 16:56:4615-16赛季CBA联赛之深圳
日期:2018-06-15 14:59:3715-16赛季CBA联赛之青岛
日期:2018-06-08 13:45:2815-16赛季CBA联赛之同曦
日期:2018-06-04 19:42:2015-16赛季CBA联赛之山东
日期:2018-05-30 12:44:59CU十四周年纪念徽章
日期:2018-05-15 11:36:3815-16赛季CBA联赛之广东
日期:2018-05-14 09:52:4215-16赛季CBA联赛之深圳
日期:2018-05-04 21:53:0815-16赛季CBA联赛之辽宁
日期:2018-04-02 14:03:3915-16赛季CBA联赛之北京
日期:2018-03-23 15:24:07
发表于 2018-07-09 18:42 |显示全部楼层
本帖最后由 wh7211 于 2018-07-09 18:57 编辑

1. 如何理解微服务,简要说明您所理解的微服务是什么?

微服务是一种架构风格,一个大型的复杂软件由一个或多个微服务组成。系统中每个微服务都可以被独立部署,各个微服务之间是松耦合的。每个微服务仅关注于完成一件任务并很好地完成任务。在所有情况下,每个任务代表这一个小的业务能力。

微服务的核心思想是一个完整的应用由多个小的、相互独立的微服务组成,这些微服务运行在自己的进程中,开发和发布都没有依赖。不同微服务通过一些轻量级交互机制来通信,服务可独立拓展伸缩,每个服务定义了明确的边界,不同的服务甚至可以采用不同的编程语言来实现,由独立团队维护。微服务的目的是为了根据业务有效拆分应用,实现敏捷开发和部署。



2. 与传统单一服务架构相比,在实战环境下,各自的优劣都有哪些?

传统单体架构和微服务架构的优劣对比如下:

微服务架构是由一系列职责单一的细粒度服务构成的分布式网状结构,服务之间通过轻量机制进行通信,一般以集群方式提供服务。

(1)微服务架构的优势

  • 模块可独立提供服务,每个服务都比较简单,只关注于一个业务功能,边界清晰,易于维护
  • 通过最佳及最合适的不同的编程语言与工具进行开发,易于引入新技术,能够做到有的放矢地解决针对性问题
  • 每个微服务可由不同团队独立开发,互不影响,加快推出市场的速度
  • 微服务商店模式,快速的组合和重构
  • 模块间松耦合,不同SLA保障计划,可以提供更高的灵活性
  • 微服务架构是持续交付(CD)的巨大推动力,允许在频繁发布不同服务的同时保持系统其它部分的可用性和稳定性
  • 更好的可扩展性和鲁棒性


(2)传统单体架构的劣势

  • 加载、编译耗时长
  • 代码管理复杂
  • 横向扩展难
  • 各模块之间的耦合程度高
  • 随着新需求的增加,更新和修复大型整体式应用越来越困难
  • 应用功能的快速上线能力差
  • 快速变化的需求受到整体式应用的限制
  • 随着应用云化的日益普及,生于云端的应用具有与传统IT不同的技术基因和开发运维模式




3. 如果您考虑部署微服务,在业务部署过程中会遇到哪些关键挑战?

会遇到微服务给DevOps带来的下列挑战:

(1)服务使用不同的编程语言开发,因此要为每种语言准备编译环境,为每个服务的部署准备不同的库和框架,让服务的开发和部署变得非常复杂;
(2)大量的微服务模块,复杂的版本管理和BUG跟踪,间接导致项目管理成本增加;
(3)分布式架构特性,服务分布在多个主机集群上,很难持续跟踪指定服务究竟运行在哪台主机上,后续的系统维护不方便;
(4)一个服务一个虚拟机,随着微服务架构不停的横向扩展,主机数量将快速增长,最小规模的主机配置可能也会超过了很多微服务对资源的要求,从而造成了超量配置并浪费开销;
(5)运维开销及成本增加,一个整体式系统如果由20个微服务组成,可能需要40-60个进程;
(6)必须具有DevOps开发运维一体化技能,具有较强DevOps技能的人员比较稀缺;
(7)隐式接口与接口匹配问题,把系统分为多个协作组件后会产生新的接口,在实际环境中,微服务架构会有更高的发布风险;
(8)代码重复,某些底层功能需要被多个服务所用,为了避免将”同步耦合引入到系统中“,有时候需要向不同服务添加同样的代码,这就会导致代码重复;
(9)分布式系统的复杂性,作为一种分布式系统,微服务引入了复杂性和其他若干问题,例如网络延迟、容错性、消息序列化、不可靠的网络、异步机制、版本化、差异化的工作负载等,开发人员需要考虑以上的分布式系统问题;
(10)异步机制,微服务往往使用异步编程、消息与并行机制,如果应用存在跨微服务的事务性处理,其实现机制会变得复杂化;
(11)可测性的挑战,在动态环境下服务间的交互会产生非常微妙的行为,难以可视化及全面测试;
(12)部署复杂,一个微服务应用一般由大批服务构成,这就形成大量需要配置、部署、扩展和监控的部分。

容器可以轻松实现微服务化后的DevOps,具备“独立性,细粒度,快速创建和销毁以及完善的管理工具”等特点的Docker可以为微服务提供一个完美的运行环境,当然,支持微服务的容器管理平台也需要解决诸如“基础架构服务管理,生命周期管理和团队协作,配置管理和部署支持”等问题。

论坛徽章:
27
IT运维版块每日发帖之星
日期:2016-04-01 06:20:0015-16赛季CBA联赛之广东
日期:2016-07-25 18:17:09C
日期:2016-10-25 16:10:552017金鸡报晓
日期:2017-02-08 10:39:4215-16赛季CBA联赛之同曦
日期:2017-02-11 13:43:1415-16赛季CBA联赛之同曦
日期:2017-05-13 19:24:3815-16赛季CBA联赛之上海
日期:2017-07-19 17:38:4415-16赛季CBA联赛之福建
日期:2017-08-02 09:45:3315-16赛季CBA联赛之山东
日期:2017-08-23 17:34:3615-16赛季CBA联赛之上海
日期:2017-11-14 09:20:5015-16赛季CBA联赛之佛山
日期:2017-12-01 10:26:3815-16赛季CBA联赛之吉林
日期:2018-03-30 12:58:43
发表于 2018-07-10 09:23 |显示全部楼层
1. 如何理解微服务,简要说明您所理解的微服务是什么?
以一个一个小的服务组成一个大的系统。框架搭建成功后,开发人员只关心服务的开发。

2. 与传统单一服务架构相比,在实战环境下,各自的优劣都有哪些?
微服务容易扩展,对于大规模的系统来说维护省力。单一服务架构适用于小系统,简单,稳定,方便。

3. 如果您考虑部署微服务,在业务部署过程中会遇到哪些关键挑战?
微服务与单一服务架构的业务是不一样的。需要重新设计。
稳定性,新东西都需要一个阶段的稳定期。


论坛徽章:
12
CU大牛徽章
日期:2013-04-17 11:20:3615-16赛季CBA联赛之福建
日期:2017-03-13 11:33:442017金鸡报晓
日期:2017-02-08 10:39:422017金鸡报晓
日期:2017-01-10 15:13:29IT运维版块每日发帖之星
日期:2016-03-15 06:20:01IT运维版块每日发帖之星
日期:2015-10-02 06:20:00CU十二周年纪念徽章
日期:2013-10-24 15:41:34CU大牛徽章
日期:2013-09-18 15:15:45CU大牛徽章
日期:2013-09-18 15:15:15CU大牛徽章
日期:2013-04-17 11:46:39CU大牛徽章
日期:2013-04-17 11:46:2815-16赛季CBA联赛之吉林
日期:2017-05-25 16:45:47
发表于 2018-07-10 15:34 |显示全部楼层
回复 3# aloki

理解和整理比较的很好,我觉得你其实不需要那本书啦,哈哈!

论坛徽章:
4
IT运维版块每日发帖之星
日期:2015-08-25 06:20:002017金鸡报晓
日期:2017-01-10 15:13:292017金鸡报晓
日期:2017-02-08 10:33:2115-16赛季CBA联赛之新疆
日期:2018-04-23 13:55:23
发表于 2018-07-11 09:36 |显示全部楼层
1. 如何理解微服务,简要说明您所理解的微服务是什么?
服务架构风格是一种将单个应用程序作为一套小型服务开发的方法,每种应用程序都在自己的进程中运行,并与轻量级机制(通常是HTTP资源API)进行通信。 这些服务是围绕业务功能构建的,可以通过全自动部署机制独立部署。 这些服务的集中管理最少,可以用不同的编程语言编写,并使用不同的数据存储技术。
2. 与传统单一服务架构相比,在实战环境下,各自的优劣都有哪些?
解耦:对于我们底层程序员而言,看得见的好处就是解耦。我要实现一个功能,可能并不需要很深入的了解别人的代码,因为程序员嘛,可能都觉得别人的代码是个渣渣([哭笑不得])。我可以新作一个微服务,这个服务为其他功能提供服务,又不依赖于原来已有的功能,至于业务逻辑,可以一边上手一边熟悉 内聚,可以独立部署:意思就是我维护的这个微服务,可以独立部署,对其他服务不会是强依赖,不会存在因为其他服务不存在而造成我自己的服务不能启动或者不可用的问题。

分布式:微服务架构下不存在一个特别大的系统包含很多中心功能,这样也能提高容错性,一个服务的瘫痪并不会让整个系统瘫痪 权限验证:微服务是高度内聚的服务,我自己的这个服务,我可以定制任意合理规则,而这个规则又只适用于我自己的服务。相比于dubbo RPC调用,http微服务调用的权限验证可以更直接更严格更定制化,而rpc调用时的权限验证,我个人始终觉得不能做的很优雅 数据分开治理,自带分库属性:原来的大系统使用一个数据库,当数据很多流量很大时,就会涉及到分库分表。

而微服务下,每个服务是否使用数据库,数据库是和其他服务公用还是自建,都有很大灵活性,即我觉得微服务自带分库分表属性 系统不会被长期限制在某个技术栈上,在微服务的架构下,整个系统不会受限于java或者nodejs 或者go,而是大家协同不冲突,全部http协议,json格式 各个模块的单元测试容易自动化 等
3. 如果您考虑部署微服务,在业务部署过程中会遇到哪些关键挑战?


论坛徽章:
4
CU大牛徽章
日期:2013-04-17 11:48:26CU大牛徽章
日期:2013-04-17 11:48:40CU大牛徽章
日期:2013-04-17 11:48:45摩羯座
日期:2013-12-06 18:10:04
发表于 2018-07-13 08:06 |显示全部楼层
1. 如何理解微服务,简要说明您所理解的微服务是什么?
万变不离其宗,都是向着模块化、标准化、高内聚低耦合的工程优化方向前进。人类各工程史无不如此发展。这东西没有具体的定义,你可以将系统做成几个独立的程序,互相之间通过REST API通讯,你能说不是微服务?但如果没有服务注册、发现、降级、断路、自动测试和部署等的配合,你可能有点不好意思说这是微服务“架构”。但它本质上就是一个微服务构成的系统,只要你做了解偶与业务边界的划分。

2. 与传统单一服务架构相比,在实战环境下,各自的优劣都有哪些?
可能没有做过的人并不能充分了解这些优劣。举两个我自己的例子:

一个是用Django开发的Web,所有的功能全在一个Django工程中完成。各功能间没有任务通讯开销,测试也非常顺畅,开发速度还是很快的,也不会出现各子系统间需要通过约定来约束接口和数据结构的情况,一个全局定义所有模块全部生效。但如果想改一个功能,必须将一个服务全部停掉才能更新。

另一个是微服务架构而成的系统,不同部分分别用了Django/Go/C++,互相之间除了通过REST接口通讯,部分还选择通过消息队列进行通讯。做单个服务的时候,是挺顺畅的,理解起来也没有阻碍,出了问题不用调试我都知道可能是哪出了问题。只是你做到D服务的时候,可能会把A、B、C服务的实现给忘了,互相之间只有约定好的接口,不看文档做根本不放心。而且,有些测试比单体服务困难,不是说构建测试困难,而是各服务之间的关系有时难以处理,有时端到端测试几乎是不可能的。你说这到底是降低是软件质量还是提高了软质量?很难说。但带来的好处也很明显,我可以单独部署、单独完成,选择合适的技术栈,横向扩展也非常方便。测试大多数时候还是比单体服务要方便的。

3. 如果您考虑部署微服务,在业务部署过程中会遇到哪些关键挑战?
最麻烦的,我觉得是测试。两三个关系不复杂的服务还好办,如果七八个服务,几十个接口,各种异步、并发,关系错综复杂,有些自动化测试根本没办法进行,或者成本极高。如果自动化测试没法进行,devops就谈不上。

另外的难点,就是服务粒度的划分,这是没有标准的,全看需求、凭经验。总地来说,前期粒度大一些,后期可以慢慢改小,但哪些可以合并到一起、哪些必须在前期就要分开,很考经验。

最后的难点,就是围绕微服务架构上的那一套了,比如服务注册、发现、降级、自动化测试和部署等等,真的全套做下来成本不低的,多数小团队没有精力去实施的。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号 北京市公安局海淀分局网监中心备案编号:11010802020122
广播电视节目制作经营许可证(京) 字第1234号 中国互联网协会会员  联系我们:wangnan@it168.com
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP