为您推荐:
精华内容
最热下载
问答
  • 5星
    8.2MB Yao__Shun__Yu 2021-08-11 16:32:43
  • 5星
    19.58MB Yao__Shun__Yu 2021-05-31 15:44:57
  • 中间件(英语:Middleware),又译中间件、中介层,是一类提供系统软件应用软件之间连接、便于软件各部件之间的沟通的软件,应用软件可以借助中间件在不同的技术架构之间共享信息与资源。中间件位于客户机服务器的...

    中间件的定义

    中间件(英语:Middleware),又译中间件、中介层,是一类提供系统软件和应用软件之间连接、便于软件各部件之间的沟通的软件,应用软件可以借助中间件在不同的技术架构之间共享信息与资源。中间件位于客户机服务器的操作系统之上,管理着计算资源和网络通信。 – 维基百科

    个人理解:

    将具体业务和底层逻辑解耦的组件,非业务的技术类组件非业务的技术类组件。是一种应用于分布式系统的基础软件,位于应用与操作系统、数据库之间,为上层应用软件提供开发、运行和集成的平台。中间件解决了异构网络环境下软件互联和互操作等共性问题,并提供标准接口、协议,为应用软件间共享资源提供了可复用的“标准件”。

    大致的效果是:

    介于操作系统和应用程序之间的产品,中间件简单解释,你可以理解为面向信息系统交互,集成过程中的通用部分的集合,屏蔽了底层的通讯,交互,连接等复杂又通用化的功能,以产品的形式提供出来,系统在交互时,直接采用中间件进行连接和交互即可,避免了大量的代码开发和人工成本。其实,理论上来讲,中间件所提供的功能通过代码编写都可以实现,只不过开发的周期和需要考虑的问题太多,逐渐的,这些部分,以中间件产品的形式进行了替代。需要利用服务的人(前端写业务的),不需要知道底层逻辑(提供服务的)的具体实现,只要拿着中间件结果来用就好了。
    

    举个例子:

    比如常见的消息中间件,即系统之间的通讯与交互的专用通道,类似于邮局,系统只需要把传输的消息交给中间件,由中间件负责传递,并保证传输过程中的各类问题,如网络问题,协议问题,两端的开发接口问题等均由消息中间件屏蔽了,出现了网络故障时,消息中间件会负责缓存消息,以避免信息丢失。相当于你想给美国发一个邮包,只需要把邮包交给邮局,填写地址和收件人,至于运送过程中的一系列问题你都不需要关心了。再比如我开了一家炸鸡店(业务端),然而周边有太多屠鸡场(底层),为了成本我肯定想一个个比价,再综合质量挑选一家屠鸡场合作(适配不同底层逻辑)。由于市场变化,合作一段时间后,或许性价比最高的屠鸡场就不是我最开始选的了,我又要重新和另一家屠鸡场合作,进货方式、交易方式等等全都要重来一套(重新适配)。然而我只想好好做炸鸡,有性价比高的肉送来就行。于是我找到了一个专门整合屠鸡场资源的第三方代理(中间件),跟他谈好价格和质量后(统一接口),从今天开始,我就只需要给代理钱,然后拿肉就行。代理负责保证肉的质量,至于如何根据实际性价比,选择不同的屠鸡场,那就是代理做的事了。

    链接:https://www.zhihu.com/question/19730582/answer/140527549

    评判关键从定义可以总结出评判的几个地方

    1. 性质:中间件是软件。
    2. 作用层级:系统软件和应用软件之间、软件各部件之间;管理客户机与系统软件之间的计算资源和网络通信。
    3. 服务对象:中间件为应用软件服务,应用软件为最终用户服务,最终用户并不直接使用中间件。
      在这里插入图片描述

    分类

    在这里插入图片描述

    中间件可以分为基础中间件、集成中间件和行业领域应用平台。其中,基础中间件是构建分布式应用的基础,也是集成中间件和行业领域应用平台的基础,包括应用服务器、消息中间件和交易中间件等。
    在这里插入图片描述

    三大基础中间件分别为交易中间件、消息中间件和应用服务器中间件,其中:

    交易中间件是:专门针对联机业务处理系统而设计的

    是所有中间件类型中理论较为成熟、功能和性能界定比较清晰的中间件产品。在联机业务处理系统中,需处理大量并发进程,涉及到操作系统、文件系统、数据通讯、数据库管理、应用软件等,通过交易中间件,可降低联机业务处理系统的开发难度,提高系统运行的安全稳定性。交易中间件主要应用在金融、财税、运输、电力、电信等行业中,如银行业务系统、电信计费系统等。

    消息队列(Message Quequing)是在消息传输过程中保存消息的容器,消息中间件即为消息队列的承载形式。

    消息是两台计算机间传送的数据单位,消息队列在将消息从它的源中继到它的目标时充当中间人,主要目的是提供路由并保证消息的传递;如果发送消息时接收者不可用,消息队列会保留消息,直到可以成功地传递它,主要解决传统结构耦合性问题、系统异步性问题以及缓解大数据量并发的问题等。

    消息队列有较多的型号,较为常用的为ActiveMQ、Rabbit MQ、RocketMQ和Kafk a。由于消息队列使用消息将应用程序连接起来,这些消息通过像Rabbit MQ的消息代理服务器在应用程序之间路由。

    应用服务器中间件位于客户浏览器和数据库之间,为应用程序提供业务逻辑的代码。

    应用服务器通过组件的应用程序接口将商业应用逻辑曝露给客户端的程序,同时为应用提供运行平台和系统服务,并管理对数据库的范围。对于高端需求,应用服务器具有高可用性监视、集群化、负载平衡、集成冗余和高性能分布式应用服务,以及对复杂的数据库访问的支持等功能。目前,市场上应用服务器平台中有J2EE,WebLogic,Glassfish,JBoss企业应用平台,以及Apache Tomcat和Apache Geronimo等。
    中间件技术发展的初衷是以适应网络技术应用的复杂性及跨平台特性为基础,是在软件产业不断发展过程中自然产生的。

    云服务

    云计算产业自下而上大体分为基础设施即服务(IaaS)、平台即服务(PaaS)、软件即服务(SaaS)三大部分,对应传统IT架构中的操作系统、中间件和应用软件。传统中间件服务一般使用专有API和专有协议,PaaS服务的特点在于开放开源,基于标准通用的API在异构系统之间实现互通互操作。根据Gartner分类,PaaS分为iPaaS(集成平台即服务)和aPaaS(应用部署和运行平台),前者侧重于PaaS与IaaS之间,实现跨多个云、云与传统应用程序之间以及公共云和私有云之间的缝集成;后者侧重于PaaS与SaaS之间,支持应用程序在云端的开发、部署和运行等。iPaaS和MWaaS成为全球中间件行业热点。根据Gartner于2018年6月发布的报告显示,企业对iPaaS(集成平台即服务)和MWaaS(中间件即服务)的投入将超越传统市场。2017年,传统中间件产品增速仅有个位数增长,而基于云和基于开源的应用集成(iPaaS)产品将继续保持两位数的增长(2017年iPaaS营收首次突破10亿美元,同增72%),是挑战者们角力的重点领域。而iPaaS的成功催生了MwaaS(中间件即服务)业务,MWaaS套件可以视为一组基于云的混合集成服务,包括云集成(iPaaS)、基于云的API平台(提供开发、运行、管理和保护API服务)、基于云的B2B集成(提供除API之外的其他服务,如EDI和MFT集成)、移动后端集成(MBaaS),、物联网集成等。以华为举例,华为重视云中间件市场,将其作为白皮书中重要细分行业。在其《鲲鹏计算产业白皮书》中测算,到2023年,全球中间件市场空间434亿美元,5年复合增长率10.3%。中国中间件市场空间13.6亿美元,5年复合增长率15.7%。且用户对于基于云的分布式应用服务、消息队列等中间件工具的需求不断增长,将会促进中间件市场的快速发展。目前,华为云中间件产品主要包括应用中间件系列产品和分布式数据库中间件(DDM)。其中,应用中间件系列产品主要包括应用管理与运维平台ServiceStage、微服务引擎CSE、分布式缓存服务Redis和Memcached、分布式消息服务(包括DMS、Kafka、RabbitMQ)、API网关APIG和云性能测试服务CPTS等。

    常见种类

    中间件是什么

    中间件是一种独立的系统软件或服务程序,分布式应用软件借助这种软件在不同的技术之间共享资源。中间件位于客户机/ 服务器的操作系统之上,管理计算机资源和网络通讯。是连接两个独立应用程序或独立系统的软件。相连接的系统,即使它们具有不同的接口,但通过中间件相互之间仍能交换信息。

    执行中间件的一个关键途径是信息传递。通过中间件,应用程序可以工作于多平台或 OS 环境。

    中间件是介于操作系统和应用软件之间,为应用软件提供服务功能的软件,有消息中间件,交易中间件,应用服务器等。由于介于两种软件之间,所以,称为中间件。

    为什么使用中间件

    具体地说,中间件屏蔽了底层操作系统的复杂性,使程序开发人员面对一个简单而统一的开发环境,减少程序设计的复杂性,将注意力集中在自己的业务上,不必再为程序在不同系统软件上的移植而重复工作,从而大大减少了技术上的负担。

    中间件带给应用系统的,不只是开发的简便、开发周期的缩短,也减少了系统的维护、运行和管理的工作量,还减少了计算机总体费用的投入。

    主要中间件的分类

    1. Hadoop
      当一个大的任务由一台机器在规定的时间内不能完成时,人们就要采用分布式计算,即很多台机器联合起来共同完成任务。换句话说,就是把大任务拆分成许多个小任务,然后再把这些小任务分配给多台计算机去完成。参与计算的多台计算机组成一个分布式系统,需要运行一系列的分布式基础算法。

    Hadoop 就是一个分布式计算平台,用 Java 语言开发,包含 Common、MapReduce 和 HDFS 三个核心部件(HDFS 和 MapReduce 是最核心的两个部件)。其中:
    Common 为 Hadoop 的其他项目提供了一些常用工具,主要包括系统配置工具 Configuration、远程过程调用 RPC、序列化机制和 Hadoop 抽象文件系统等。
    MapReduce 是处理海量数据的计算模型。
    而 HDFS 用于存储海量数据,它具备高度容错性,能在低成本的通用硬件机器上稳定运行。

    Hadoop 实现了分布式计算中的基础算法(如一致算法、选举算法、故障检测、快照等),同时为用户提供了编程和命令接口。程序员调用这些函数能轻松写出分布式应用程序,我们都知道,如果一切从头开始,要完成一个分布式程序的编写是异常艰难的。

    Hadoop 在海量非结构化数据处理方面能充分展示它的优势,如消费者购买行为分析、商品推荐、关键词检索、信贷风险评估等。

    如图 1 所示,Hadoop 其实就是一个分布式计算平台,它“覆盖”在操作系统之上,向上提供函数调用(API)和命令接口,在水平方向完成分布式系统的基础算法。作为编程人员和用户,只要了解 API 和命令即可。
    在这里插入图片描述
    图 1 Hadoop

    基于 Hadoop 平台衍生出来的开源项目主要有 Yarn、HBase、Hive、ZooKeeper、Avro、Sqoop、Mahout、Crossbow 等。

    以 Hadoop 为基础的生态目前已经成为大数据的标准方案,被广泛用于金融、市场、电信、交通等行业的海量数据分析,在即将到来的大数据时代,它将会发挥更大的作用。

    在中国,很多行业(如银行、电信、移动、电力、石油、交通等)沉淀了大量的业务数据,对这些海量数据进行挖掘和分析,将会带来巨大的价值。

    用 Hadoop 构建的应用实例对于计算资源的消耗具备两个明显的特征:
    资源需求大:表明 Hadoop 需要大量的存储、计算和网络带宽。
    资源需求具备季节性:表明除存储需求是经常性占用外,在运行 Mapreduce 时才需要大量的计算和网络资源,而分析大量数据的工作并不是经常性的——称为季节性

    因此,云计算是大数据天生的计算资源供应途径,云计算的资源弹性很好地满足了大数据的季节性计算资源需求。也就是说,大数据是云计算经典的应用案例。当然,也可以按照大数据对计算资源的波峰需求静态配给计算资源,但是这种方案会造成资源的巨大浪费。
    2. LVS
    LVS 是 Linux Virtual Server 的首字母缩写,意为 Linux 虚拟服务器,即把许多台物理 Linux 计算机逻辑上整合成一台超级计算机,对用户来说感觉只有一台计算能力很强的服务器,如图 2 所示。

    LVS 就是一个由软件实现的负载均衡器,工作在网络 OSI 的第四层(应用层),是中国人章嵩开发的,代码已经并入了 Linux 内核。利用它,再加上一台廉价的计算机,就能构建一台企业级的负载均衡器。而那些外国大公司的负载均衡器,售价都要十几万元,甚至几十万元,便宜的也要几万元,LVS 出来后,这些产品都不得不降价。

    负载均衡器的作用就是把任务分配给最合适的服务器。比如一个大型购物网店,有 100 台同样配置的服务器在运行,如果某一时刻有 10 万用户在线购物,那么通过负载均衡器,每台服务器差不多承担 1000 个在线购物用户。

    LVS 的官网网站是 http://www.linuxvirtualserver.org。另外,两个较为流行的第七层负载均衡器是 Nginx 和 HAProxy,针对应用做均衡,所以能适应的负载种类没有 LVS 多。
    在这里插入图片描述
    LVS原理图

    1. Linux-HA
      也许有读者会问:“负载均衡器本身故障怎么办?”是的,如果负载均衡器出现故障,那么整个系统(如网店)将会瘫痪。所以人们开发了各种集群软件,如 Linux-HA 和 Keepalive 等,而微软干脆就在 Windows 服务器版中集成故障转移集群软件。

    集成故障转移集群软件的核心思想是,实时检测故障机器并及时让好的机器接管工作,对外提供高可用性。Linux-HA 意为 Linux 高可用性项目,此项目具体包含如下几个组件。
    在这里插入图片描述

    通过心跳信号(Heartbeat)检测故障,一台好的计算机会不断向其他计算机发送心跳信号,也会接收其他计算机发送过来的心跳信息。当在规定的时间内没有收到对方计算机的心跳信号时,就启动应急预案,进一步确认故障并准备接管那台计算机的任务。

    例如,我们采用两台 LVS 计算机,并分别安装和配置 Linux-HA,一台 LVS 计算机作为工作机,另一台作为备份机,两台 LVS 计算机互相监督对方的运行状态。当工作机故障时,备份机接管负载均衡任务并报警。相反,当备份机出故障时,只报警,提醒技术员维修备份机。

    两台LVS计算机同时出故障是比较糟糕的情况,不过这种情况发生的概率很小,除非机房断电或者遭到雷击。对于一些非常关键的应用,可以增加参与负载均衡的服务器数量来提高可靠性,如民航飞机上采用 5 台服务器。
    4. 静态网站服务器
    我们浏览一家公司的网站时,很可能就是跟那家公司服务器上的 Apache 程序打交道,网页浏览器与 Apache 成了标准的 C/S 模式,浏览器是客户端,而 Apache 是服务端。Apache 首先把主页对应的文件 index.html 发给我们,我们看到主页内容后,点击主页上的某个链接,它又把该链接对应的文件发给我们,过程如图 3 所示。
    访问静态网页的过程
    在这里插入图片描述

    图 3 访问静态网页的过程

    配合 PHP 引擎,Apache 也支持 PHP 动态网页。过程为:

    1)当 Apache 收到用户要浏览的 PHP 文件后,把这个 PHP 文件发给 PHP 执行引擎。

    2)PHP 执行引擎执行该 PHP 文件,产生一个临时的静态网页文件并发回给 Apache。

    3)最后 Apache 把这个临时的静态网页文件发给用户。

    采用 Perl、Python 和 Ruby 脚本语言编写的动态网页,其工作过程与 PHP 类似。

    Apache 是最流行的开源网站服务器,在世界排名前 100 万的网站中,有 60.6% 的网站采用 Apache;在排名前 1000 的大型网站中,Apache 占到了 34.5%,而 Ngnix 占到了 34.9%,略胜于 Apache。
    5. 动态应用服务器
    开源的动态应用服务器有 JBoss、Tomcat、Geronimo、JOnAS,关于这些项目更详细的介绍,请参考相应的官方网站。

    推荐

    常见的中间件有哪些
    1.一般本地开发的话,小项目,或者是个人开发建议使用tomcat。
    2.linux系统建议使用jetty或apache hpptd
    3.大型的项目就用JBOSS或webloigc

    4.大项目或者商业项目一般采用:weblgoic/webshere,其他的还有jboss、glasshfish等
    5.一些示例项目或者小项目常采用jetty

    6.tomcat , jboss, weblogic, websphere 一般项目tomcat就可以了

    Tomcat是Sun的JSWDK(JavaServer Web Development Kit)中Servlet的运行环境(servlet容器)。Tomcat是Apache Jakarta软件组织的一个子项目,Tomcat是一个JSP/Servlet容器,它是在SUN公司的JSWDK(Java Server Web Development Kit)基础上发展起来的一个JSP和Servlet规范的标准实现,使用Tomcat可以体验JSP和Servlet的最新规范。经过多年的发展,Tomcat不仅是JSP和Servlet规范的标准实现,而且具备了很多商业Java Servlet容器的特性,并被一些企业用于商业用途。

    JBoss是一个运行EJB的J2EE应用服务器。它是开放源代码的项目,遵循最新的J2EE规范。从JBoss项目开始至今,它已经从一个EJB容器发展成为一个基于的J2EE的一个web 操作系统(operating system for web),它体现了J2EE规范中最新的技术

    WebLogic服务器是企业级的应用服务器,支持EJB, 集群以及 ERP(企业资源计划)的连通性 ,开发公司:BEA。

    WebSphere产品系列是IBM公司一套典型的电子商务应用开发工具及运行环境

    Tomcat 介绍 如今,基于Web的应用越来越多,传统的Html已经满足不了如今的需求。我们需要一个交互式的Web,于是便诞生了各种Web语言。
    如Asp,Jsp,Php等。当然,这些语言与传统的语言有着密切的联系,如Php基于C和C++语言,Jsp基于Java语言。Tomcat即是一个Jsp和Servlet
    的运行平台。
    Tomcat是一个免费的开源的Serlvet容器,它是Apache基金会的Jakarta项目中的一个核心项目,由Apache,Sun和其它一些公司及个人共同开发
    而成。由于有了Sun的参与和支持,最新的Servlet和Jsp规范总能在Tomcat中得到体现。Tomcat被JavaWorld杂志的编辑选为2001年度最具创新
    的java产品,可见其在业界的地位。
    Tomcat最新版本是4.0x.4.0x与3.x的架构不同,而是重新设计的。Tomcat4.0x中采用了新的Servlet容器:Catalina,完整的实现了Servlet2.3
    和Jsp1.2规范。Tomcat提供了各种平台的版本供下载,可以从http://jakarta.apache.org上下载其源代码版或者二进制版。由于Java的跨平台
    特性,基于Java的Tomcat也具有跨平台性。
    与传统的桌面应用程序不同,Tomcat中的应用程序是一个WAR(WebArchive)文件。WAR是Sun提出的一种Web应用程序格式,与JAR类似,也是许
    多文件的一个压缩包。这个包中的文件按一定目录结构来组织:通常其根目录下包含有Html和Jsp文件或者包含这两种文件的目录,另外还会有
    一个WEB-INF目录,这个目录很重要。通常在WEB-INF目录下有一个web.xml文件和一个classes目录,web.xml是这个应用的配置文件,而
    classes目录下则包含编译好的Servlet类和Jsp或Servlet所依赖的其它类(如JavaBean)。通常这些所依赖的类也可以打包成JAR放到WEB-INF
    下的lib目录下,当然也可以放到系统的CLASSPATH中,但那样移植和管理起来不方便。
    在Tomcat中,应用程序的部署很简单,你只需将你的WAR放到Tomcat的webapp目录下,Tomcat会自动检测到这个文件,并将其解压。你在浏览器
    中访问这个应用的Jsp时,通常第一次会很慢,因为Tomcat要将Jsp转化为Servlet文件,然后编译。编译以后,访问将会很快。另外Tomcat也提
    供了一个应用:manager,访问这个应用需要用户名和密码,用户名和密码存储在一个xml文件中。通过这个应用,辅助于Ftp,你可以在远程通
    过Web部署和撤销应用。当然本地也可以。
    Tomcat不仅仅是一个Servlet容器,它也具有传统的Web服务器的功能:处理Html页面。但是与Apache相比,它的处理静态Html的能力就不如
    Apache.我们可以将Tomcat和Apache集成到一块,让Apache处理静态Html,而Tomcat处理Jsp和Servlet.这种集成只需要修改一下Apache和
    Tomcat的配置文件即可。
    另外,Tomcat提供Realm支持。Realm类似于Unix里面的group.在Unix中,一个group对应着系统的一定资源,某个group不能访问不属于它的资
    源。Tomcat用Realm来对不同的应用(类似系统资源)赋给不同的用户(类似group)。没有权限的用户则不能访问这个应用。Tomcat提供三种
    Realm,1:JDBCRealm,这个Realm将用户信息存在数据库里,通过JDBC获得用户信息来进行验证。2:JNDIRealm,用户信息存在基于LDAP的服
    务器里,通过JNDI获取用户信息。3:MemoryRealm,用户信息存在一个xml文件里面,上面讲的manager应用验证用户时即使用此种Realm.通过
    Realm我们可以方便地对访问某个应用的客户进行验证。
    在Tomcat4中,你还可以利用Servlet2.3提供的事件监听器功能,来对你的应用或者Session实行监听。Tomcat也提供其它的一些特征,如与SSL
    集成到一块,实现安全传输。还有Tomcat也提供JNDI支持,这与那些J2EE应用服务器提供的是一致的。说到这里我们要介绍一下通常所说的应
    用服务器(如WebLogic)与Tomcat有何区别。应用服务器提供更多的J2EE特征,如EJB,JMS,JAAS等,同时也支持Jsp和Servlet.而Tomcat则功
    能没有那么强大,它不提供EJB等支持。但如果与JBoss(一个开源的应用服务器)集成到一块,则可以实现J2EE的全部功能。既然应用服务器
    具有Tomcat的功能,那么Tomcat有没有存在的必要呢?事实上,我们的很多中小应用不需要采用EJB等技术,Jsp和Servlet已经足够,这时如果
    用应用服务器就有些浪费了。而Tomcat短小精悍,配置方便,能满足我们的需求,这种情况下我们自然会选择Tomcat.
    基于Tomcat的开发其实主要是Jsp和Servlet的开发,开发Jsp和Servlet非常简单,你可以用普通的文本编辑器或者IDE,然后将其打包成WAR即
    可。我们这里要提到另外一个工具Ant,Ant也是Jakarta中的一个子项目,它所实现的功能类似于Unix中的make.你需要写一个build.xml文件,
    然后运行Ant就可以完成xml文件中定义的工作,这个工具对于一个大的应用来说非常好,我们只需在xml中写很少的东西就可以将其编译并打包
    成WAR.事实上,在很多应用服务器的发布中都包含了Ant.另外,在Jsp1.2中,可以利用标签库实现Java代码与Html文件的分离,使Jsp的维护更
    方便。
    Tomcat也可以与其它一些软件集成起来实现更多的功能。如与上面提到的JBoss集成起来开发EJB,与Cocoon(Apache的另外一个项目)集成起
    来开发基于Xml的应用,与OpenJMS
    集成起来开发JMS应用,除了我们提到的这几种,可以与Tomcat集成的软件还有很多。
    Tomcat确实是一个很好的工具,不仅仅因为其免费,功能强大,更因为其开放性。如今,开源软件越来越收到人们的重视,Linux就是一个成功
    的典型。

    多种中间件(Tomcat, Apache, Nginx, MQ,等)各项性能参数设置、监控及优化;

    特点

    一、中间件是什么?
    中间件(英语:Middleware)顾名思义是系统软件和用户应用软件之间连接的软件,以便于软件各部件之间的沟通,特别是应用软件对于系统软件的集中的逻辑,是一种独立的系统软件或服务程序,分布式应用软件借助这种软件在不同的技术之间共享资源。中间件在客户服务器的操作系统、网络和数据库之上,管理计算资源和网络通信。总的作用是为处于自己上层的应用软件提供运行与开发的环境,帮助用户灵活、高效地开发和集成复杂的应用软件。

    也就是说,关于中间件,我们可以理解为:是一类能够为一种或多种应用程序合作互通、资源共享,同时还能够为该应用程序提供相关的服务的软件。中间件是一类软件统称,而非一种软件;中间件不仅仅实现互连,还要实现应用之间的互操作。
    在这里插入图片描述 中间件示意图

    中间件的特点:

    满足大量应用的需要;
    运行于多种硬件和OS平台;
    支持分布计算,提供跨网络、硬件和OS平台的透明性的应用或服务的交互;
    支持标准的协议;
    支持标准的接口。

    展开全文
    lockhou 2021-03-17 07:57:51
  • 在基于go的web服务,常常需要进行用户的权限验证,一般会使用JWT,但是在gin我们也可以通过自定义中间件来实现用户的权限验证。 目录 1.基于gin中间件的用户验证 2.结合casbin的gin的中间件的用户权限验证 ...

    在基于go的web服务中,常常需要进行用户的权限验证,一般会使用JWT,但是在gin中我们也可以通过自定义中间件来实现用户的权限验证,在gRPC中可以通过拦截器来实现。

    目录

    1.基于gin中间件的用户验证

    2.结合casbin的gin的中间件的用户权限验证

    (1) 建立conf文件

    (2) 建立用户权限列表csv文件

    (3) 使用gin中间件进行权限验证

    (4) 测试

    (5) 扩展

    3.gRPC中的Token认证

    (1)gRPC中的拦截器

    (2)UnaryServerInterceptor的使用

    (3)StreamServerInterceptor的使用

    (4)在服务中注册拦截器

    4.总结

     

    1.基于gin中间件的用户验证

    有些时候我们可能只需要简单的用户认证,例如restful接口,当用户登陆之后后台返回给调用者一个token,之后所有的请求头部都会携带上这个token,然后后端拿到请求的数据,如果请求头部中的token验证通过,那么就认为具有相应的权限。这种情况我们可以通过自定义gin中的中间件来实现。

    package main
    
    import (
    	"github.com/casbin/casbin/v2"
    	"github.com/gin-gonic/gin"
    	"log"
    	"net/http"
    )
    
    func main() {
    	r := gin.Default()
    	r.Use(authorizationWithCasbin())
    	r.GET("/test", func(c *gin.Context) {
    		 c.JSON(http.StatusOK, gin.H{"user": "admin", "secret": "admin@123"})
    	})
    	_ = r.Run(":8080")
    }
    
    // 自定义的用户验证的中间件
    func authorization() gin.HandlerFunc {
    	return func(c *gin.Context) {
    		if userName, passWord, ok := c.Request.BasicAuth();!ok{
    			c.AbortWithStatus(401)
    		}else{
    			if userName != "seu" || passWord != "admin@123"{
    				c.AbortWithStatus(401)
    			}
    		}
    	}
    }

    但是需要注意的的是c.Request.BasicAuth的使用,我们可以看一下它的源代码如下:

    // BasicAuth returns the username and password provided in the request's
    // Authorization header, if the request uses HTTP Basic Authentication.
    // See RFC 2617, Section 2.
    func (r *Request) BasicAuth() (username, password string, ok bool) {
    	auth := r.Header.Get("Authorization")
    	if auth == "" {
    		return
    	}
    	return parseBasicAuth(auth)
    }
    
    // parseBasicAuth parses an HTTP Basic Authentication string.
    // "Basic QWxhZGRpbjpvcGVuIHNlc2FtZQ==" returns ("Aladdin", "open sesame", true).
    func parseBasicAuth(auth string) (username, password string, ok bool) {
    	const prefix = "Basic "
    	// Case insensitive prefix match. See Issue 22736.
    	if len(auth) < len(prefix) || !strings.EqualFold(auth[:len(prefix)], prefix) {
    		return
    	}
    	c, err := base64.StdEncoding.DecodeString(auth[len(prefix):])
    	if err != nil {
    		return
    	}
    	cs := string(c)
    	s := strings.IndexByte(cs, ':')
    	if s < 0 {
    		return
    	}
    	return cs[:s], cs[s+1:], true
    }

    可以看到它是先获取请求头部中的Authorization字段,然后再去解析,并且该字段的值必须是以Basic 开头,后面是对应的userName:userInfo的base64编码形式。例如,我们的用户名是seu,密码是admin@123,首先我们获取seu:admin@123的base64编码为c2V1OmFkbWluQDEyMw==(这里为了方便起见我直接将返回的token用用户的密码进行替代),最终请求头部的Authorization字段就是Basic c2V1OmFkbWluQDEyMw==。我们可以使用Goland中的HttpClient发送Get请求进行验证

    GET http://localhost:8080/test
    Accept: application/json
    Authorization: Basic c2V1OmFkbWluQDEyMw==
    输出:
    # {
      "secret": "admin@123",
      "user": "admin"
    }
    
    GET http://localhost:8080/test
    Accept: application/json
    Authorization: Basic c2V1OmFkbWluQDEyMw===
    输出:
    # Response code: 401 (Unauthorized); Time: 96ms; Content length: 0 bytes
    

    2.结合casbin的gin的中间件的用户权限验证

    有些时候我们需要更复杂的权限验证,比如特定的用户只能请求某些特定的restful接口,这个时候我们可以使用casbin来帮助我们进行权限的验证。关于casbin大家可以参考以下官网文档和相关文章

    Github: https://github.com/casbin/casbin

    Document: https://casbin.org/docs/en/overview

    相关文章: https://cloud.tencent.com/developer/article/1534674

    概括的说就是在使用casbin之前我们需要先建立一个model的控制文件,以及对应的用户权限列表,用户权限列表可以存在mysql中或者是csv中,然后还是和上面一样,根据请求头部中的Authorization字段去获取用户名,然后根据用户名去拉取用户权限,再使用casbin进行权限的比对来判断该用户是否具有相关的权限。

    例如现在有2个用户Tom和Bob,其中Tom只能以GET的方式访问/testTom这个接口,Bob只能以POST的方式访问/testBob这个接口,我们可以通过以下的方式来实现这样要求

    (1) 建立conf文件

    [request_definition]
    r = sub, obj, act
    
    [policy_definition]
    p = sub, obj, act
    
    [policy_effect]
    e = some(where (p.eft == allow))
    
    [matchers]
    m = r.sub == p.sub && r.obj == p.obj && r.act == p.act

     其中request_definition中定义的是请求的字段,sub,obj,act可以理解成分别代表用户的名称,用户要操作的对象和用户要进行的操作。相对应的policy_definition中即为对应的用户权限列表。

    (2) 建立用户权限列表csv文件

    p,Tom, /testTom, GET
    p,Bob, /testBob, POST

    (3) 使用gin中间件进行权限验证

    package main
    
    import (
    	"github.com/casbin/casbin/v2"
    	"github.com/gin-gonic/gin"
    	"log"
    	"net/http"
    )
    
    func main() {
    	r := gin.Default()
    	r.Use(authorizationWithCasbin())
    	r.GET("/testTom", func(c *gin.Context) {
    		 c.JSON(http.StatusOK, gin.H{"user": "Tom"})
    	})
    	r.POST("/testBob", func(c *gin.Context) {
    		c.JSON(500, gin.H{"user": "Bob"})
    	})
    	_ = r.Run(":8080")
    }
    
    
    func authorizationWithCasbin() gin.HandlerFunc {
    	return func(c *gin.Context) {
    		if userName, passWord, ok := c.Request.BasicAuth();!ok{
    			c.AbortWithStatus(401)
    		}else{
    			// 这里可以根据用户名称去拉取密码和用户信息进行进一步的验证
    			if passWord == "admin@123" {
    				e, err := casbin.NewSyncedEnforcer("model.conf", "user.csv")
    				if err != nil{
    					log.Print(err)
    				}
    				sub := userName
    				obj := c.Request.URL.String()
    				act := c.Request.Method
    				if ok, _ := e.Enforce(sub, obj, act);!ok{
    					c.AbortWithStatus(401)
    				}
    			}else{
    				c.AbortWithStatus(401)
    			}
    		}
    	}
    }

    我们首先获取对应的信息,然后使用casbin进行验证即可

    (4) 测试

    我们还是使用Goland自带的HttpClient对其进行验证

    (1)Tom:admin@123
    GET http://localhost:8080/testTom
    Accept: application/json
    Authorization: Basic VG9tOmFkbWluQDEyMw==
    >>> {"user": "Tom"}
    
    (2)Bob:admin@123
    GET http://localhost:8080/testTom
    Accept: application/json
    Authorization: Basic Qm9iOmFkbWluQDEyMw==
    >>> Response code: 401 (Unauthorized); Time: 96ms; Content length: 0 bytes
    
    (3)Tom:admin@123
    POST http://localhost:8080/testBob
    Accept: application/json
    Authorization: Basic VG9tOmFkbWluQDEyMw==
    >>> Response code: 401 (Unauthorized); Time: 93ms; Content length: 0 bytes
    
    (4)
    POST http://localhost:8080/testBob
    Accept: application/json
    Authorization: Basic VG9tOmFkbWluQDEyMw==
    >>> >>> {"user": "Bob"}

    (5) 扩展

    使用casbin我们可以很方便的进行权限修改与扩展,例如我们现在想要所有的用户都可以访问/testTom这个接口,对应的我们只需要修改conf文件和csv文件如下:

    [request_definition]
    r = sub, obj, act
    
    [policy_definition]
    p = sub, obj, act
    
    [policy_effect]
    e = some(where (p.eft == allow))
    
    [matchers]
    m = (r.sub == p.sub && r.obj == p.obj && r.act == p.act) || p.sub == "*"
    p,*, /testTom, GET
    p,Bob, /testBob, POST

    但是有些时候我们需要自定义验证的方式,例如文件可能存储在其他地方或者数据库中,这个时候我们可以去自己继承casbin中的四个接口 

    type Adapter interface {
    	// LoadPolicy loads all policy rules from the storage.
    	LoadPolicy(model model.Model) error
    	// SavePolicy saves all policy rules to the storage.
    	SavePolicy(model model.Model) error
    
    	// AddPolicy adds a policy rule to the storage.
    	// This is part of the Auto-Save feature.
    	AddPolicy(sec string, ptype string, rule []string) error
    	// RemovePolicy removes a policy rule from the storage.
    	// This is part of the Auto-Save feature.
    	RemovePolicy(sec string, ptype string, rule []string) error
    	// RemoveFilteredPolicy removes policy rules that match the filter from the storage.
    	// This is part of the Auto-Save feature.
    	RemoveFilteredPolicy(sec string, ptype string, fieldIndex int, fieldValues ...string) error
    }

    这样我们就可以自定义任何我们需要的验证方式,代码示例可以查看:https://github.com/JustKeepSilence/gdb/blob/master/db/route.go 

    3.gRPC中的Token认证

    上面介绍的是如何在gin中进行token认证,如果使用的是gRPC,同样的我们可以使用官方提供的拦截器很容易的实现token认证,详情可以参考官方文档:https://pkg.go.dev/google.golang.org/grpc#UnaryClientInterceptor,接下来就以我自己的项目GDB中的例子来说明如何使用拦截器使用token认证。详细的代码可以参考github: https://github.com/JustKeepSilence/gdb

    (1)gRPC中的拦截器

    在gRPC中服务端有两种拦截器,针对一般函数的拦截器UnaryServerInterceptor和针对流函数的StreamServerInterceptor拦截器,它们的定义分别如下

    # UnaryServerInterceptor 
    type UnaryServerInterceptor func(ctx context.Context, req interface{}, info *UnaryServerInfo, handler UnaryHandler) (resp interface{}, err error)
    
    # StreamServerInterceptor 
    type StreamServerInterceptor func(srv interface{}, ss ServerStream, info *StreamServerInfo, handler StreamHandler) error

    其中,UnaryServerInterceptor的参数分别为client传进来的context,client的请求req,服务端的信息info和用来处理请求的handler。StreamServerInterceptor的参数分别为客户端的请求参数srv,服务端的流信息ss和info以及用来处理请求的handler。

    (2)UnaryServerInterceptor的使用

    基本逻辑还是和前述一样,在客户端登陆的时候,首先将用户信息写入context中,然后在服务端获取用户信息并进行验证,如果验证通过则返回token信息,以后客户端的每次请求都必须携带这个token信息,我们也可以基于这个token进行更加详细的权限控制。

    下面是服务端使用UnaryServerInterceptor进行权限验证的代码

    func (s *server) authInterceptor(c context.Context, req interface{}, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (resp interface{}, err error) {
    	if s.configs.Authorization {
    		methods := strings.Split(info.FullMethod, "/")
    		if md, ok := metadata.FromIncomingContext(c); !ok {
    			return nil, status.Errorf(codes.Unauthenticated, "invalid token")
    		} else {
    			var userName string
    			if d, ok := md["userName"]; ok {
    				userName = d[0]
    			} else {
    				return nil, status.Errorf(codes.Unauthenticated, "invalid token")
    			}
    			remoteAddress := md.Get(":authority")[0] // address
    			userAgent := md.Get("user-agent")[0]     // user agent
    			if methods[len(methods)-1] == "UserLogin" {
    				r := req.(*pb.AuthInfo)
    				if result, err := s.gdb.userLogin(authInfo{
    					UserName: r.GetUserName(),
    					PassWord: r.GetPassWord(),
    				}, remoteAddress, userAgent); err != nil {
    					return nil, status.Errorf(codes.Unauthenticated, "invalid token")
    				} else {
    					return &pb.UserToken{Token: result.Token}, nil
    				}
    			} else {
    				var token string
    				if d, ok := md["token"]; ok {
    					token = d[0]
    				} else {
    					return nil, status.Errorf(codes.Unauthenticated, "invalid token")
    				}
    				if v, err := s.gdb.infoDb.Get([]byte(userName+"_token"+"_"+remoteAddress+"_"+userAgent), nil); err != nil || v == nil {
    					return nil, status.Errorf(codes.Unauthenticated, "invalid token")
    				} else {
    					if token != fmt.Sprintf("%s", v) {
    						return nil, status.Errorf(codes.Unauthenticated, "invalid token")
    					} else {
    						// log handler
    						return handler(c, req)
    					}
    				}
    			}
    		}
    	} else {
    		return handler(c, req)
    	}
    }

    其中server为对应的rpc服务的结构体。基本的逻辑为首先根据配置文件中的配置来判断用户是否要进行权限控制,如果确定进行权限控制的话,首先判断请求要客户端的方法,如果是登陆方法的话则直接获取用户信息,并进行验证,如果验证通过,则返回token信息,对于其他的请求方法,则获取token字段与数据库中的token信息进行比对

    (3)StreamServerInterceptor的使用

    StreamServerInterceptor的使用和UnaryServerInterceptor基本相同,下面是服务端的代码

    func (s *server) authWithServerStreamInterceptor(srv interface{}, ss grpc.ServerStream, info *grpc.StreamServerInfo, handler grpc.StreamHandler) error {
    	if s.configs.Authorization {
    		if !info.IsClientStream {
    			return status.Errorf(codes.Unknown, "unknown service type")
    		} else {
    			if md, ok := metadata.FromIncomingContext(ss.Context()); !ok {
    				return status.Errorf(codes.Unauthenticated, "invalid token")
    			} else {
    				var userName, token string
    				remoteAddress := md.Get(":authority")[0] // address
    				userAgent := md.Get("user-agent")[0]     // user agent
    				if d, ok := md["userName"]; ok {
    					userName = d[0]
    				} else {
    					return status.Errorf(codes.Unauthenticated, "invalid token")
    				}
    				if d, ok := md["token"]; ok {
    					token = d[0]
    				} else {
    					return status.Errorf(codes.Unauthenticated, "invalid token")
    				}
    				if v, err := s.gdb.infoDb.Get([]byte(userName+"_token"+"_"+remoteAddress+"_"+userAgent), nil); err != nil || v == nil {
    					return status.Errorf(codes.Unauthenticated, "invalid token")
    				} else {
    					if token != fmt.Sprintf("%s", v) {
    						return status.Errorf(codes.Unauthenticated, "invalid token")
    					} else {
    						return handler(srv, ss)
    					}
    				}
    			}
    		}
    	} else {
    		return handler(srv, ss)
    	}
    }

    也是获取请求中的token信息并进行对应的验证

    (4)在服务中注册拦截器

    在实现完了拦截器之后,我们还需要在启动gRPC服务之前去进行注册,并且现在官方已经支持了链式注册,也就是说我们可以使用多个拦截器,而不需要像以前一样将所有的逻辑都放在一个函数中,对于UnaryServerInterceptor使用ChainUnaryInterceptor,对于StreamServerInterceptor则使用ChainStreamInterceptor,使用代码如下

    s = grpc.NewServer(grpc.ChainUnaryInterceptor(se.panicInterceptor, se.authInterceptor, se.logInterceptor),
    			grpc.ChainStreamInterceptor(se.panicWithServerStreamInterceptor, se.authWithServerStreamInterceptor))

    可以看到,我这里注册了三个拦截器,分别是panic拦截器,auth拦截器和log拦截器,并且拦截器的运行顺序和注册的顺序是一致的。

    4.总结

    在go的后台开发中,token的权限验证是很常见的问题,不管是常见的web后台还是grpc后台,我们都可以很容易实现这种需求。如果想要了解更详细的代码细节,大家可以参考我的github:https://github.com/JustKeepSilence/gdb或者与我交流~

    展开全文
    qq_39778055 2021-03-15 18:27:16
  • 人们在使用中间件时,往往是一组中间件集成在一起,构成一个平台(包括开发平台运行平台),但在这组中间件中必须要有一个通信中间件,即中间件=平台+通信,这个定义也限定了只有用于分布式系统才能称为中间件,...

    1、什么是中间件

    中间件(Middleware)是处于操作系统和应用程序之间的软件,也有人认为它应该属于操作系统中的一部分。人们在使用中间件时,往往是一组中间件集成在一起,构成一个平台(包括开发平台和运行平台),但在这组中间件中必须要有一个通信中间件,即中间件=平台+通信,这个定义也限定了只有用于分布式系统中才能称为中间件,同时还可以把它与支撑软件和实用软件区分开来。
    举例:

    1,RMI(Remote Method Invocations, 远程调用)
    2,Load Balancing(负载均衡,将访问负荷分散到各个服务器中)
    3,Transparent Fail-over(透明的故障切换)
    4,Clustering(集群,用多个小的服务器代替大型机)
    5,Back-end-Integration(后端集成,用现有的、新开发的系统如何去集成遗留的系统)
    6,Transaction事务(全局/局部)全局事务(分布式事务)局部事务(在同一数据库联接内的事务)
    7,Dynamic Redeployment(动态重新部署,在不停止原系统的情况下,部署新的系统)
    8,System Management(系统管理)
    9,Threading(多线程处理)
    10,Message-oriented Middleware面向消息的中间件(异步的调用编程)
    11,Component Life Cycle(组件的生命周期管理)
    12,Resource pooling(资源池)
    13,Security(安全)
    14,Caching(缓存)

    2、为什么需要使用消息中间件

    具体地说,中间件屏蔽了底层操作系统的复杂性,使程序开发人员面对一个简单而统一的开发环境,减少程序设计的复杂性,将注意力集中在自己的业务上,不必再为程序在不同系统软件上的移植而重复工作,从而大大减少了技术上的负担。中间件带给应用系统的,不只是开发的简便、开发周期的缩短,也减少了系统的维护、运行和管理的工作量,还减少了计算机总体费用的投入。

    3、中间件特点

    为解决分布异构问题,人们提出了中间件(middleware)的概念。中间件是位于平台(硬件和操作系统)和应用之间的通用服务,如下图所示,这些服务具有标准的程序接口和协议。针对不同的操作系统和硬件平台,它们可以有符合接口和协议规范的多种实现。

    在这里插入图片描述

    也许很难给中间件一个严格的定义,但中间件应具有如下的一些特点:

    (1)满足大量应用的需要
    (2)运行于多种硬件和OS平台
    (3)支持分布计算,提供跨网络、硬件和OS平台的透明性的应用或服务的交互
    (4)支持标准的协议
    (5)支持标准的接口
    由于标准接口对于可移植性和标准协议对于互操作性的重要性,中间件已成为许多标准化工作的主要部分。对于应用软件开发,中间件远比操作系统和网络服务更为重要,中间件提供的程序接口定义了一个相对稳定的高层应用环境,不管底层的计算机硬件和系统软件怎样更新换代,只要将中间件升级更新,并保持中间件对外的接口定义不变,应用软件几乎不需任何修改,从而保护了企业在应用软件开发和维护中的重大投资。

    简单说:中间件有个很大的特点,是脱离于具体设计目标,而具备提供普遍独立功能需求的模块。这使得中间件一定是可替换的。如果一个系统设计中,中间件是不可替换的,不是架构、框架设计有问题,那么就是这个中间件,在别处可能是个中间件,在这个系统内是引擎。

    4、在项目中什么时候使用中间件技术

    在项目的架构和重构中,使用任何技术和架构的改变我们都需要谨慎斟酌和思考,因为任何技术的融入和变化都可能人员,技术,和成本的增加,中间件的技术一般现在一些互联网公司或者项目中使用比较多,如果你仅仅还只是一个初创公司建议还是使用单体架构,最多加个缓存中间件即可,不要盲目追求新或者所谓的高性能,而追求的背后一定是业务的驱动和项目的驱动,因为一旦追求就意味着你的学习成本,公司的人员结构以及服务器成本,维护和运维的成本都会增加,所以需要谨慎选择和考虑。

    但是作为一个开放人员,一定要有学习中间件技术的能力和思维,否则很容易当项目发展到一个阶段在去掌握估计或者在面试中提及,就会给自己带来不小的困扰,在当今这个时代这些技术也并不是什么新鲜的东西,如果去掌握和挖掘最关键的还是自己花时间和花精力去探讨和研究。

    中间件技术概览

    在这里插入图片描述

    总结:
    总的来说,中间件技术的诞生就是为了解决分布式结构中多服务之间产生的消息沟通等一系列问题,为的就是适应复杂服务和分布式架构。其中包括消息中间件,负载均衡,缓存,多数据库处理中间件。

    参考资料

    https://www.kuangstudy.com/zl/rabbitmq#1365935694551306242

    展开全文
    david2000999 2021-11-08 19:56:08
  • 在互联网应用开发初期,所有用于支撑系统建设的,框架结构、基础工具、业务逻辑、功能服务包括页面展示等,都是在一个系统开发完成,最终也只是把系统数据库部署在同一服务器上。 但随着互联网应用的发展,...

     一、前言

    在互联网应用开发初期,所有用于支撑系统建设的,框架结构、基础工具、业务逻辑、功能服务包括页面展示等,都是在一个系统中开发完成,最终也只是把系统和数据库部署在同一台服务器上。

    但随着互联网应用的发展,业务体量逐渐增大,那么原有的系统搭建就很难支撑起现有的业务体量。因此开始陆续出现应用与数据库分离、Nginx 反向代理、缓存组件、分组部署、RPC 分布式应用、网关服务、监控系统等等。

    在这些系统的架构的演进过程中,不断的出现各类支撑起服务建设升级的系统和中间件。在中间件这一层的建设,基本是来自于业务系统中非业务逻辑的通用性核心功能抽离出来的,而逐步形成各类中间件服务。

    中间件:是介于操作系统和应用软件之间,为应用软件提供服务功能的软件,有消息中间件,通信中间件,应用服务器等。由于介于两种软件之间,所以,称为中间件。

    二、中间件的起源

    最早具有中间件技术思想以及功能实现的软件是 IBM 的 CICS,但由于 CICS 不是分布式环境下的产品,因此大家一般把 Tuxedo 作为第一个严格意义上的中间件。

    Tuxedo 是1984年在当时属于AT&T的贝尔实验室开发完成,但由于分布式处理当时并没有在商业应用上获得像今天一样的成功,Tuxedo 在很长一段时期里只是实验室的产品,后来被 Novell 收购,在经过 Novell 并不成功的商业推广后,1995年被现在的 BEA 公司收购。

    尽管中间件的概念很早就已经产生,但中间件技术的广泛运用却是在最近10年之中。BEA 公司1995年成立后收购 Tuxedo 才成为一个真正的中间件厂商,IBM 的中间件 MQSeries 也是20世纪90年代的产品,其他许多中间件产品也都是最近几年才成熟起来的。

    三、为什么使用中间件

    使用中间件来自于中间件本身的价值能力,具体的说中间件屏蔽了底层操作系统的复杂性,让开发工程师可以把更多的专注力放在业务系统的逻辑和流程实现上,让开发人员面对的是一个简单、单一、统一的开发环境,减少程序设计因底层差异而导致的复杂度。

    中间件最终带给系统的是交付质量和交付能力的提升,它的存在不只是让开发简单、周期短,更主要的是减少了系统上线后的不稳性和运维成本以及管理的工作量,同时还减少了服务资源的投入。

    四、中间件的分类

    其实中间件的分类有很多中,这可能也是让大家在平常的开发中迷惑,到底哪些是中间件。一些基本的中间件定义很好定位,比如MQ、RPC、Dapper等等,但有些软件服务虽然不是作为中间件开发出来的,但它们如果符合中间件的定义,也可以归纳到中间的范畴里。

    按照 IDC 的分类方法,中间件可以分为六类:

    1. 终端仿真/屏幕转换中间件

    此类中间件用以实现客户机端的图形用户接口与现有的服务器端字符接口方式的应用程序之间的互操作。例如;中继器、IO板卡、PLC等作为控制层进行高级语言与展示层的交互。

    1. 数据访问中间件

    JDBC、ODBC,此类中间件适用于应用程序与各类数据源的通信操作,以便于直接访问和更新基于服务器的数据源,数据源可以是关系型、非关系型以及对象型,大概你可以想到的是 Mysql、Oracle、Redis 或者 Elasticsearch 等,使用此类中间件可以更好的简化应用系统的开发。

    1. 远程过程调用中间件

    RPC,是最早的分布式应用系统采用的一种同步请求与应答协议,RPC 扩展了过程开发中的“功能调用和结果返回”机制,使得它可以适应于远程环境调用和分布式部署。

    1. 消息中间件

    kafka、ActiveMQ、RabbitMQ,现在的分布式系统构建中都离不开 RPC 与 MQ,系统架构设计中使用消息中间件把应用扩展到不同的操作系统和不同的网络环境中,基于消息事件驱动机制处理业务逻辑的解耦和消峰。

    1. 交易中间件

    此类中间件是一种针对联机交易处理系统而设计的中间件,其实很多业务发起的中间件都属于此类。交易中间件就相当于一组程序模块,使用它可以大大的减少开发一个交易系统所需要的编程工作量。

    1. 对象中间件

    对于这样的中间件分类也可以理解为是从业务系统中抽离出具有通用性通用功能的核心逻辑,面向对象的技术基本是 Java 语言的最大目标,通过封装、继承、多态,提供良好的代码重用性。

    五、你为什么要懂中间件开发

    说到底你只面向工作学习吗?

    如果说编程只是单纯的承接产品需求开发系统功能,那么基本可以把程序开发过程,简单理解为按照需求PRD,定义属性创建方法调用展示,这三个步骤。

    尤其是在一些大公司中,会有易用的、完善的、标准的架构体系和运维服务,例如:RPC、MQ、Redis集群、分布式任务、配置中心、分库分表组件、网关等搭配出来的系统架构。也因此让程序员做到只关心业务功能开发

    但让程序员只关心业务开发,有成熟的系统架构、有标准的开发流程、有通用的功能设计,对于团队效能提升来说是非常好的事。可一部分程序员正因为有这样的好事,日复一日的岁月做着同样的事,最后成为工具人。

    如果是框架和中间件的存在,是了让程序员只关心业务开发。 那为什么你面试的时候会被问到核心组件的设计和原理呢? 在这个年代,别放弃学习以及深度学习是你几乎唯一的生存途径。所以你要多去拓展学习一些更核心的技术,让自己成为那个最贵的程序员!

    展开全文
    song_hai_lei 2021-11-19 18:26:29
  • qwq1503 2021-01-04 11:29:48
  • weixin_29461699 2021-03-01 07:23:06
  • weixin_42886699 2021-12-02 00:32:30
  • qq_42937522 2021-02-19 17:14:52
  • weixin_42350411 2021-08-09 04:20:52
  • weixin_42166623 2021-08-07 05:23:30
  • g6U8W7p06dCO99fQ3 2021-02-20 11:23:00
  • u022812849 2021-06-15 21:12:18
  • qq_60387497 2021-11-19 12:43:32
  • Neverdrophair 2021-11-28 21:14:23
  • luolan_hust 2021-02-06 14:31:00
  • qq_58268157 2021-10-18 00:02:08
  • weixin_39977136 2021-02-26 14:07:17
  • shizhengye 2021-09-27 10:45:53
  • m0_54024707 2021-10-17 16:32:33
  • zhipengfang 2021-06-01 21:03:29
  • u012702547 2021-12-13 17:08:53
  • weixin_32017023 2021-04-10 14:58:03
  • miachen520 2021-09-12 22:05:09
  • qq_45796208 2021-10-24 22:26:40
  • Linuxhus 2021-07-14 16:24:39
  • skydust1979 2021-02-20 18:53:38
  • weixin_36059283 2021-03-15 15:34:04
  • wangaolong0427 2021-10-29 11:33:33

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 116,962
精华内容 46,784
关键字:

中间件和中台

友情链接: LiLunLiXueKeHouZuoYe.rar