OSCHINA 问答合集[2]:我有一套高峰期每秒钟约有 1 万人下单的系统,遇到了关于 Java 高并发的问题

开源中国问答区新栏目“OSCHINA 问答合集”上线啦,本期收录了 5 月高热度的问题及回复(吐槽),希望能让你有所收获~! 本期问答合集收录的问题,动辄就是“千万”级别的场景,这让大家“面试造火箭”的那些本领终于可以有用武之地了。 而关于程序员职业生涯方面,有妹子问到“女生做架构师是否靠谱”,我们热心肠的 oscer 岂会袖手旁观? 不多说了,各位接着阅读大家的精彩回答吧~! 进入问答区: 你可以在技术问答版块畅聊技术 你可以在职业生涯版块寻道解惑 你可以在IT大杂烩版块和大家谈笑风生 我们希望: 这里可以成为一个能让大家有所收获的地方。因此,这里拒绝攻击、拒绝谩骂、拒绝无脑黑。 这里可以沉淀大家各种的技术问题。无论是新手的基础问题,还是高端玩家的资深问题,都是有价值的。 这是一个更纯粹讨论技术的地方,能给程序员提供一片友好交流的清净之地,不懂的可以在这里寻找帮助,懂的可以在这里帮助别人。 总之, 在这里你可以向所有人提问。 反正你的问题可能会没答案。;-) ==========分割线========== 开源中国技术问答 @飞扬的梦 :关于Java高并发的问题 我有一套系统,高峰期每秒钟约有1万人下单,平均每个用户下28件商品,系统延迟要求在30毫秒响应客户。 请问,我要怎样做才能保证库存不会超,重点是30毫秒内客户端就要响应。实测使用redis,如果集群的话,会导致库存超,不集群的话,redis没过一会就崩溃了,有时间数据会出错。 数据库用mysql的,写入没有太多的问题。现在主要问题是在redis性能上。 >>>@公孙二狗  从问题来看,楼主应该经验不怎么丰富,但是能有这么牛逼的业务的公司,轻轻松松拿出几个亿来开发这种项目应该不是问题,大把的人才,怎么可能到论坛找方案呢。 >>>@Storm-Cai  这个问题归根到底还是库存控制。下单过程、查商品校验啥的都没问题,redis集群能解决问题。 库存保证如果需要时间响应优先,则可以采用redis集群中原子操作,每种商品做一个k-v的库存数量,下单该商品就库存减1,如果28件商品需要写28次redis,可以并行去写。库存数量以redis中为准。 追问:公司上一代架构是这样做的,但是redis性能上限,导致每秒最多只能28万订单入库。现在改了架构了,不过变成单机版的。我在寻找一下,既可以集群高可用,速度又快的方案。 哦,看明白你的意思了。你是说即时采用库存数量全部放redis,每个redis实例存一个商品库存,一共28个商品实例,一秒也只能有28WTPS?可以这样,采用内存分区数据分段校验。以上是说,不存redis了,你项目不是集群的么,跑多少个实例,库存就分多少片。假设商品库存10000个,你跑了四个服务,那么每个服务就只能下单2500个成功,前端负载均衡策略采用轮询。 这样的方案你来多少都没啥问题,前提是预先要把库存设好,在启动抢购这类活动前,要保证每个服务进程内数据都对,不然会导致库存对不上。 假设商品A有库存10000个,你跑了四个服务,进程内每个库存数量就是2500个,采用原子递减去减库存。异步同步数据到数据库就是了。这种方案也是我采用的方案,效果杠杠的。有个不好的地方就是活动进行中服务绝对不能宕机……….. >>>@keepthinker  采用Redis Cluster或自己搭建逻辑集群(自己做key哈希分散到不同节点),采用计数器分片(Redis incr操作),假如分片100个,总共100w个商品,那么每个分片计数器最大值为10000,假如有进程计数器对加1后超过最大值则认为没库存,一个redis 8W TPS,假如计数器平均分散到每台Redis机器,就能最多支持100 * 8W TPS的分布式计数器,Redis数量越多,那么就能无限逼近800W TPS。 对于这种写入峰值高的订单入库要求,那么当然得采用高可用队列进行削峰限流写入MySQL数据库。 >>>@Chet_W  hash分散,将不同的商品和交易信息存在不同的redis >>>@抢小孩糖吃  应该做流量控制,通过流量控制分散库存请求到具体的Cache,并对竞争做队列处理,消耗库存。多一步流量控制解决具体导向哪个队列服务,降低多节点对单一Redis的竞争。 @emo奋斗 :我有一个打击物流、电商假货的app思路,请大神们提提意见 1.每个产品生产出来自动生成一个独立二维码; 2.如果有包装,每个包装(单个或集合包装)也自动生成独立二维码; 3.打包(单个或集合打包)或者拆包时对包装和产品进行关联或者解除关联; 4.产品每到一个环节的关联或解除关联,通过二维码记录时间、地点(精确定位)、主要动作(流转、打包、拆包)、关联主体; 5.每一次关联都对每个app中已记录信息进行更新; 6.下一各关联主体关联产品必须获取上一个关联主体的授权; 7.流通环节关联主体均必须获得首端主体的授权方可注册,终端环节具有查询权限,可获取所有产品流通关联信息; 8.只要保障首端不出问题,保证所有被授权流通环节出货均为正品。 >>>@程序猿猴  产品溯源系统, 你本质就是解决信任问题,这正是区块链解决的问题。 随之带来的就是复杂的操作流程和高昂的成本。 如果产品要溯源的话,这个问题就复杂了,比如说一件衣服的溯源吧: 1. 涤纶/棉原料溯源 2. 涤纶/棉制作原料溯源 甚至还要往下追溯好几层,成本可观 现在物流体系的各个系统其实监管都还比较严格,想要造假需要几个部门的联合操作,一个物流系统可能由:omc,tms,wms等系统组成,如果想调换一个货物,则需要仓库工作人员和系统操作人员联合操作才能实现。 >>>@苍暮之星  这一套方案可行的前提是没有内鬼,这个只能防外人,不能防止业务流上的工作人员舞弊。而这套方案偏偏又是防内鬼的,不然谁能够在物流途中更换商品?没有可行性啊。再说了,像顺丰等成熟的物流体系,人家内部本身就有这类制度,甚至有时候会故意在包裹里塞上标识物,现在出问题的都是收件环节和发件环节,也就是最小的收发点会出这种换货的可能性。 追问:从生产出来已经开始读取产品信息了,并且每个环节的有效读取和非有效读取都是有记录的,而且有效读取信息需要专门授权。至于最后的销售环节,存在掉包产品的可能性,不过正常来讲,只能通过销售代理单位销售。所以,一方面从非代理单位购买本身就难以避免假货;另一方面,流通信息可随时记录、查询,一物多卖很容易被查出;再者,在以上两个条件下,最后销售环节更换商品的代价太大,会被取消资格。 >>>@飘摇清风  感觉像类似mes的应用,人工、管控成本过高,从成本上考虑不一定能行。不知道您是否知道用假的400电话验证假货的防伪码,一条龙服务,价格也不高,别指望每个人都会去官网验证。 追问:主要的问题是,信息关联共享。400验证码是可以复印的,这个你复印下来,只要扫描就知道流向。这个我想是适用于稍微高端的产品,买个棒棒糖就不至于了。而且,在我看来没有什么运营成本。 运营成本只是成本中的一种,而我提到的人工成本不只运营人工,还包括生产人工成本、仓储人工成本。对于高附加值产品可以忽略这点成本,而对于那些低附加值的,搞这套东西只会死得更快。 我举的400例子只是想说,对于量大、火爆产品,只要利润够高,造假者能生生模拟出一套验证机制,这样你这个追溯机制直接就能跳过了。 所以说你这机制书面意义比较大,实用性还需要再研究研究。 @Death黎明 :除了spring我们还有什么? 最近在公司修改了几个旧的项目,发现这几个旧的项目都没有使用任何的框架,这对长期使用spring的我感觉到十分的吃力,艰难的完成任务后心中浮现除了这个问题:     除了spring我们还有什么? spring可以极大的提高我们的开发效率,这使得在培训班出身的我的眼中spring几乎成为了java的代名词。 我感觉这很不对劲,希望去学习一些可以抛开spring的东西,希望大家给我些建议。 >>>@很拽De土豆  现在主流的java web框架,一套是以servlet为标准的spring,struts,jfinal等框架,目前主流基本都是这个。还有其它的比如actframework,playframework等无servlet的框架。 如果你使用java的话,基本离不开这2种类型。如果抛开spring的话,你可以选一种你自己喜欢的类型,自己封装一个简单的框架,理解学习,比如你可以看看smartframework,它从无到有讲解怎么写一个简单的java web框架。 […]

龙生   15 Jun 2018
View Details

10 款程序员必备的免费开源安全工具,助你成为极客

信息安全工程师、网络安全产品以及相关的技术和流程都需要耗费企业大量的成本,对于大部分企业来说,往往会缩减这一部分的支出,因此许多开发人员都会首选免费的开源安全工具。 事实上,无论是学习,试验,还是在生产基础上进行部署,安全专业人员长期以来都将开源软件视为其工具包的重要组成部分。本文我们将盘点10个你应该知道的IT安全工具包: 1、Nessus 对于几代IT安全专业人士来说,意识到网络的脆弱性始于Tenable的Nessus。Nessus是最受欢迎的漏洞扫描器,也是目前第三大流行安全程序。Nessus有免费版和商业版本。Nessus 7.1.0是一个商业版本,目前只有2005年的版本仍然是开源且免费的。 2、Snort 如果说Nessus是IT安全工程师学习漏洞扫描的起点,那么Snort就是几代IT安全人员学习入侵检测系统(IDS)知识的起点。 Snort最大的价值在于有三种工作模式:嗅探器、数据包记录器、网络入侵检测系统模式。因此,它可以是自动化安全系统的核心,也可以是一系列商业产品的组件。Snort目前归思科所有,Snort有一个活跃的社区,开源安全工具名单中如果没有Snort,那这个名单一定不完整。 3、Nagios Nagios是一个监视系统运行状态和网络信息的监视系统。与许多其他开源软件包一样,Nagios也提供免费和商业版本。 Nagios Core是开源项目的核心,基于免费的开源版本。可以查看网络状态,各种系统问题,以及日志等等。大约有50个基于Nagios开发的“官方”插件和超过3000个社区贡献的插件。 Nagios的用户界面可以通过桌面,Web或移动平台的前端进行修改,并且可以通过其中一种可用的配置工具来管理配置。 4、Ettercap Ettercap是一个Linux和BSD系统下的多用途数据包嗅探程序,也已经被移植到Windows平台下。如果你需要测试企业网络以抵御中间人攻击(MITM),那么Ettercap肯定是你首选。因为自2001年首次发布以来,该方案一直在做一件事 – 发起MITM攻击。 5、Infection Monkey Infection Monkey是一款由以色列安全公司GuardiCore在2016黑帽大会上发布的数据中心安全检测工具,其主要用于数据中心边界及内部服务器安全性的自动化检测。用户界面也是Infection Monkey的显着特点之一,尽管一些开源安全项目提供了极简主义的UI或依赖于GUI的插件或皮肤,但Infection Monkey具有与许多商业软件工具相同的GUI。 该工具在架构上,则分为Monkey(扫描及漏洞利用端)以及C&C服务器(相当于reporter,但仅仅只是用于收集monkey探测的信息)。 6、Delta Delta是一个SDN安全评估框架,作为开放网络基金会(ONF)的一个项目,它有两个主要功能: ● 它可以在不同的环境中自动实例化针对SDN元素的攻击事件, ● 它可以帮助发现SDN部署中未知的安全问题。 7、Cuckoo sandbox 有很多方法可以判断一个文件是否是安全的,但这些方法都存在一定的风险,Cuckoo sandbox是一款著名的开源沙箱系统,用于安全的测试文件,基于虚拟化环境所建立的恶意程序分析系统能自动执行并且分析程序行为。 8、Sleuth Kit 弄清楚攻击中发生的事情可能是防止未来入侵的关键一步。Sleuth Kit是一个基于CLI的取证工具和库的集合,它可以用于从磁盘映像中恢复丢失的文件,以及为了特殊事件进行磁盘映像分析。 Sleuth Kit是Autopsy的基础,Autopsy是一个GUI前端,可为大多数用户提供更快,更轻松的分析。两者都在积极发展之中,并且拥有大量充满活力的用户群体,为新功能和新功能做出贡献。 9、Lynis Lynis是一个为系统管理员提供的 Linux和Unix的审计工具 。 Lynis扫描系统的配置,并创建概述系统信息与安全问题所使用的专业审计。 Lynis源代码托管在GitHub上,它还拥有一个活跃的开发社区,主要支持来自其创建者Cisofy。Lynis的特殊功能之一是,由于其Unix基础,它能够对流行的IoT开发板(包括Raspberry Pi)进行扫描和评估。 10、Certbot 加密对许多安全标准都很重要,实施加密可能会很复杂并且代价高昂,但EFF已经试图通过像Certbot这样的工具来减少这些困扰,Certbot是一个开源的自动客户端,可以为你的Web服务器提取和部署SSL / TLS证书。 最后,希望本文提到的这些开源安全工具可以帮到你。 来源:开源最前线   from:https://www.oschina.net/news/96979/10-open-source-cyber-security-tools

龙生   12 Jun 2018
View Details

C# 导出 Excel 的各种方法总结

第一种:使用 Microsoft.Office.Interop.Excel.dll 首先需要安装 office 的 excel,然后再找到 Microsoft.Office.Interop.Excel.dll 组件,添加到引用。

第一种方法性能实在是不敢恭维,而且局限性太多。首先必须要安装 office(如果计算机上面没有的话),而且导出时需要指定文件保存的路径。也可以输出到浏览器下载,当然前提是已经保存写入数据。   第二种:使用 Aspose.Cells.dll 这个 Aspose.Cells 是 Aspose 公司推出的导出 Excel 的控件,不依赖 Office,商业软件,收费的。 可以参考:http://www.cnblogs.com/xiaofengfeng/archive/2012/09/27/2706211.html#top

设置单元格格式为文本方法:

第二种方法性能还不错,而且操作也不复杂,可以设置导出时文件保存的路径,还可以保存为流输出到浏览器下载。   第三种:Microsoft.Jet.OLEDB 这种方法操作 Excel 类似于操作数据库。下面先介绍一下连接字符串:

Provider:驱动程序名称 Data Source:指定 Excel 文件的路径 Extended Properties:Excel 8.0 针对 Excel 2000 及以上版本;Excel 12.0 针对 Excel 2007 及以上版本。 HDR:Yes 表示第一行包含列名,在计算行数时就不包含第一行。NO 则完全相反。 IMEX:0 写入模式;1 读取模式;2 读写模式。如果报错为“不能修改表 sheet1 的设计。它在只读数据库中”,那就去掉这个,问题解决。

这种方法需要指定一个已经存在的 Excel 文件作为写入数据的模板,不然的话就得使用流创建一个新的 Excel 文件,但是这样是没法识别的,那就需要用到 Microsoft.Office.Interop.Excel.dll 里面的 Microsoft.Office.Interop.Excel.Workbook.SaveCopyAs() 方法另存为一下,这样性能也就更差了。 使用操作命令创建的表都是在最后面的,前面的也没法删除(我是没有找到方法),当然也可以不再创建,直接写入数据也可以。   第四种:NPOI NPOI 是 POI 项目的.NET版本,它不使用 Office COM 组件,不需要安装 Microsoft Office,目前支持 Office 2003 和 2007 版本。 NPOI 是免费开源的,操作也比较方便,下载地址:http://npoi.codeplex.com/

PS:操作 2003 版本需要添加 NPOI.dll […]

龙生   11 Jun 2018
View Details

Docker容器进入的4种方式

在使用Docker创建了容器之后,大家比较关心的就是如何进入该容器了,其实进入Docker容器有好几多种方式,这里我们就讲一下常用的几种进入Docker容器的方法。 进入Docker容器比较常见的几种做法如下: 使用docker attach 使用SSH 使用nsenter 使用exec 一、使用docker attach进入Docker容器 Docker提供了attach命令来进入Docker容器。 接下来我们创建一个守护态的Docker容器,然后使用docker attach命令进入该容器。 $ sudo docker run -itd ubuntu:14.04 /bin/bash 然后我们使用docker ps查看到该容器信息,接下来就使用docker attach进入该容器 $ sudo docker attach 44fc0f0582d9 可以看到我们已经进入到该容器中了。   但在,使用该命令有一个问题。当多个窗口同时使用该命令进入该容器时,所有的窗口都会同步显示。如果有一个窗口阻塞了,那么其他窗口也无法再进行操作。 因为这个原因,所以docker attach命令不太适合于生产环境,平时自己开发应用时可以使用该命令。 二、使用SSH进入Docker容器 在生产环境中排除了使用docker attach命令进入容器之后,相信大家第一个想到的就是ssh。在镜像(或容器)中安装SSH Server,这样就能保证多人进入 容器且相互之间不受干扰了,相信大家在当前的生产环境中(没有使用Docker的情况)也是这样做的。但是使用了Docker容器之后不建议使用ssh进入到Docker容 器内。关于为什么不建议使用,请参考如下文章: 为什么不需要在 Docker 容器中运行 sshd 三、使用nsenter进入Docker容器 在上面两种方式都不适合的情况下,还有一种比较方便的方法,即使用nsenter进入Docker容器。关于什么是nsenter请参考如下文章: https://github.com/jpetazzo/nsenter 在了解了什么是nsenter之后,系统默认将我们需要的nsenter安装到主机中 如果没有安装的话,按下面步骤安装即可(注意是主机而非容器或镜像) 具体的安装命令如下: $ wget https://www.kernel.org/pub/linux/utils/util-linux/v2.24/util-linux-2.24.tar.gz $ tar -xzvf util-linux-2.24.tar.gz $ cd util-linux-2.24/ $ ./configure --without-ncurses $ make nsenter $ sudo cp nsenter /usr/local/bin 安装好nsenter之后可以查看一下该命令的使用。 nsenter可以访问另一个进程的名称空间。所以为了连接到某个容器我们还需要获取该容器的第一个进程的PID。可以使用docker inspect命令来拿到该PID。 docker inspect命令使用如下: $ sudo docker inspect --help    inspect命令可以分层级显示一个镜像或容器的信息。比如我们当前有一个正在运行的容器   可以使用docker inspect来查看该容器的详细信息。 $ sudo docker inspect 44fc0f0582d9   由其该信息非常多,此处只截取了其中一部分进行展示。如果要显示该容器第一个进行的PID可以使用如下方式 $ sudo docker inspect -f {{.State.Pid}} 44fc0f0582d9   在拿到该进程PID之后我们就可以使用nsenter命令访问该容器了。 $ sudo nsenter --target 3326 --mount --uts --ipc --net --pid $ sudo nsenter --target 3326 --mount --uts --ipc --net --pid 其中的3326即刚才拿到的进程的PID 当然,如果你认为每次都输入那么多参数太麻烦的话,网上也有许多做好的脚本供大家使用。 地址如下: http://yeasy.gitbooks.io/docker_practice/content/container/enter.html http://www.tuicool.com/articles/eYnUBrR   四、使用docker exec进入Docker容器 除了上面几种做法之外,docker在1.3.X版本之后还提供了一个新的命令exec用于进入容器,这种方式相对更简单一些,下面我们来看一下该命令的使用: $ sudo docker exec --help   接下来我们使用该命令进入一个已经在运行的容器 $ sudo docker ps $ sudo docker exec -it 775c7c9ee1e1 /bin/bash   from:https://www.cnblogs.com/xhyan/p/6593075.html

龙生   09 Jun 2018
View Details

解决:64位的电脑装VirtualBox新建虚拟电脑都是32位的系统

本人亲测可用,绝对原创。 转载请注明出处:http://blog.csdn.net/cherrycheng_/article/details/45719719 问题截图: 解决办法: 1.先进入BIOS,(比如我的Thinkpad,就是F12),如下图 2.进入App Menu-->Setup界面,如下图 3.进入Security --> Virtualization,如下图 4.进入Virtualization,打开服务 5.开机,打开就成功了,最终效果如下图 转载请注明出处:http://blog.csdn.net/cherrycheng_/article/details/45719719

龙生   09 Jun 2018
View Details

将 ASP.NET MVC 应用程序迁移到 Windows 容器

在 Windows 容器中运行现有的 .NET Framework 应用程序不需要对应用程序进行任何更改。 若要在 Windows 容器中运行应用程序,请创建包含应用程序的 Docker 映像,然后启动容器。 本主题介绍了如何获取现有的 ASP.NET MVC 应用程序,并在 Windows 容器中进行部署。 从现有的 ASP.NET MVC 应用程序入手,然后使用 Visual Studio 生成已发布的资产。 使用 Docker 创建包含并运行应用程序的映像。 转到在 Windows 容器中运行的网站,验证应用程序是否正常运行。 本文可确保基本了解 Docker。 若要了解 Docker,请参阅 Docker 概述。 在容器中运行的应用程序是一个随机回答问题的简单网站。 此应用程序是一款不具备身份验证或数据库存储的基本 MVC 应用程序,让你可以专心处理将 Web 层移到容器中。 后续主题将演示如何在容器化应用程序中移动和管理永久性存储。 移动应用程序涉及以下步骤: 创建发布任务以生成映像资产。 生成将运行应用程序的 Docker 映像。 启动用于运行映像的 Docker 容器。 使用浏览器验证应用程序。 完成的应用程序位于 GitHub 上。 系统必备 开发计算机必须运行 Windows 10 周年更新(或更高版本)或 Windows Server 2016(或更高版本)。 用于 Windows 的 Docker – 稳定版 1.13.0 或 1.12 beta 版本 26(或更高版本) Visual Studio 2017。 重要 如果使用的是 Windows Server 2016,请按容器主机部署 – Windows Server 中的说明操作。 安装并启动 Docker 后,右键单击托盘图标,然后选择“切换到 Windows 容器”。 必须先这样做,才能在 Windows 上运行 Docker 映像。 此命令需要几秒钟执行: 发布脚本 将需要加载到 Docker 映像中的所有资产都汇集到一处。 可以使用 […]

龙生   08 Jun 2018
View Details

大话微服务架构之微服务框架微软ServiceFabric正式开源(三)

选择315这天分享一个好框架-ServiceFabric,它于昨天正式开源了! 微软的 Azure Service Fabric 的官方博客在2017.3.24日发布了一篇博客 Service Fabric .NET SDK goes open source ,介绍了社区呼声最高的 Service Fabric 开源的情况以及当前的情况,当时开源了 Service Fabric的.NET SDK 部分,社区一直在期盼着 Service Fabric 的正式开源,经过了一年漫长的等待,2018年3月14日微软终于开源了 Service Fabric ,而且是以 MIT 许可下开放源代码,在官方博客宣布 https://blogs.msdn.microsoft.com/azureservicefabric/2018/03/14/service-fabric-is-going-open-source。 目前微软在 Github 上的开源地址是 https://github.com/Microsoft/service-fabric,目前的代码构建适用于 Linux 的 Service Fabric ,运行基本测试,有问题可以在上面提交 issue 和 PR 了,Windows 构建环境以及完整的 CI 环境还没有迁移过来。Windows 内部为 Service Fabric 开发了将近十年的内部服务,其中大部分时间都是微软内部平台,比如 Office365,Azure Stack 平台等,这意味着我们有近十年的内部微软工具可以在迁移之前完成迁移和流程细化,逐步全部开源,以后全部开发都在开源模式下进行开发工作。 微软去年漫长的一年时间里也开放了非常多的代码,包括包括 Reliable Services,Reliable Actors 和 ASP.NET Core 集成库,Azure 基础架构服务以及 Azure SQL DB,Azure Cosmos DB 和 Cortana 等大型解决方案都在使用 Service Fabric 构建。 Service Fabric 会带来如下好处: 支持创建无状态和有状态的微服务,通过云平台来伸缩他们,以应对高复杂度、低延迟、数据密集的情况 通过应用程序级别的感知和洞察,为微服务带来编排和自动化的优势 解决分布式系统诸如状态管理这样的难点,为开发人员提供应用程序生命周期管理的能力以便随着业务的增长无需重构系统架构 相关工具会集成到 Visual Studio 中,也会提供相应命令行工具,以便开发人员能够快速和轻易地上手 同时支持.NET和Java,这个特性特别适合目前国内原来很多投资于 .NET 平台。 那么接下来,我们主要来详细看下Service Fabric是什么?有哪些特性? […]

龙生   08 Jun 2018
View Details

Windows 容器

什么是容器 容器是一种将应用程序包装到其自身隔离空间内的方法。 位于容器中的应用不了解该容器外存在的所有其他应用程序或进程。 应用程序成功运行所需的所有依赖项也存在于此容器内。 无论容器移动到何处,应用程序都将始终得到满足,因为应用程序与其运行所需的一切都已绑定在一起。 这就好像是一个厨房。 我们打包所有的电器和家具、锅碗瓢盆、洗洁精和毛巾。 这便是我们的容器 我们现在可以带着这个容器,将它放在任何喜欢的入住公寓中,厨房还会是这个厨房。 我们所需做的全部工作就是为它接通水电,然后我们便可以立即开始烹饪(因为我们拥有所有需要的器具!) 容器在很大程度上就像是这个厨房。 可以有不同类型的房间以及许多相同类型的房间。 重要的一点是容器与其所需的一切内容打包在一起。 在此处观看简短概述:基于 Windows 的容器:使用企业级控制的现代应用开发。 容器基础知识 容器是独立的、资源受控制的和可移植的运行时环境,在主机或虚拟机上运行。 在容器中运行的应用程序或进程与所有需要的依赖项和配置文件打包在一起;在它看来,容器之外似乎没有任何其他进程在运行。 容器的主机为容器预配一组资源,且容器只会使用这些资源。 在容器看来,除了已经为其提供的资源之外,不存在其他资源,因此它不能接触到可能已为相邻容器预配的资源。 在你开始创建和使用 Windows 容器时,以下关键概念将会很有用。 容器主机:使用 Windows 容器功能配置的物理或虚拟计算机系统。 容器主机将运行一个或多个 Windows 容器。 容器映像:在对容器文件系统或注册表进行修改时(如软件安装),将在沙盒中捕获这些修改。 在许多情况下,你可能希望捕获此状态,以便可以创建继承这些更改的新容器。 这就是映像的本质:一旦容器停止,你便可以放弃该沙盒,或者可以将其转换为新的容器映像。 例如,让我们想象你已从 Windows Server Core 操作系统映像部署一个容器。 然后你将 MySQL 安装到此容器中。 从此容器创建新映像将充当该容器的可部署版本。 此映像将只包含所做的更改 (MySQL),但是将充当容器操作系统映像之上的一个层。 沙盒:容器启动后,将在此“沙盒”层中捕获所有的写入操作,如文件系统修改、注册表修改或软件安装。 容器操作系统映像:从映像部署容器。 容器操作系统映像是可能组成容器的许多映像层中的第一层。 此映像提供操作系统环境。 容器操作系统映像是不可变的。 也就是说,不能对其进行修改。 容器存储库:每次创建容器映像时,容器映像及其依赖项都会存储在本地存储库中。 这些映像可以在容器主机上重复使用多次。 容器映像还可以存储在公共或私有注册表(如 DockerHub)中,以便可以在许多不同的容器主机上使用它们。 对于熟悉虚拟机的人员而言,容器可能具有令人难以置信的相似性。 容器在操作系统上运行、具有文件系统,并且可以通过网络访问,就像它是物理或虚拟计算机系统一样。 话虽如此,但容器背后的技术和概念与虚拟机有很大不同。 Microsoft Azure 专家 Mark Russinovich 有一篇精彩的博客文章详述了这些差异。 Windows 容器类型 Windows 容器包括两个不同的容器类型或运行时。 Windows Server 容器 – 通过进程和命名空间隔离技术提供应用程序隔离。 Windows Server 容器与容器主机和该主机上运行的所有容器共享内核。 这些容器不提供敌对安全边界,不应该用于隔离不受信任的代码。 由于共享内核空间,这些容器要求具有相同的内核版本和配置。 Hyper-V 隔离 – 通过在高度优化的虚拟机中运行每个容器,在由 Windows Server 容器提供的隔离上扩展。 在此配置中,容器主机的内核不与相同主机上的其他容器共享。 这些容器旨在托管敌对多租户,并且具有与虚拟机相同的安全保证。 由于这些容器与主机或主机上的其他容器不共享内核,它们可运行(与受支持的版本)采用不同版本和配置的内核 – 例如 Windows […]

龙生   08 Jun 2018
View Details

NET编程之事件总线(Event Bus)

1. 引言 事件总线这个概念对你来说可能很陌生,但提到观察者(发布-订阅)模式,你也许就很熟悉。事件总线是对发布-订阅模式的一种实现。它是一种集中式事件处理机制,允许不同的组件之间进行彼此通信而又不需要相互依赖,达到一种解耦的目的。 我们来看看事件总线的处理流程: 了解了事件总线的基本概念和处理流程,下面我们就来分析下如何去实现事件总线。 2.回归本质 在动手实现事件总线之前,我们还是要追本溯源,探索一下事件的本质和发布订阅模式的实现机制。 2.1.事件的本质 我们先来探讨一下事件的概念。都是读过书的,应该都还记得记叙文的六要素:时间、地点、人物、事件(起因、经过、结果)。 我们拿注册的案例,来解释一下。 用户输入用户名、邮箱、密码后,点击注册,输入无误校验通过后,注册成功并发送邮件给用户,要求用户进行邮箱验证激活。 这里面就涉及了两个主要事件: 1,注册事件:起因是用户点击了注册按钮,经过是输入校验,结果是是否注册成功。 2,发送邮件事件:起因是用户使用邮箱注册成功需要验证邮箱,经过是邮件发送,结果是邮件是否发送成功。 其实这六要素也适用于我们程序中事件的处理过程。开发过WinForm程序的都知道,我们在做UI设计的时候,从工具箱拖入一个注册按钮(btnRegister),双击它,VS就会自动帮我们生成如下代码: void btnRegister_Click(object sender, EventArgs e) { // 事件的处理 } 其中object sender指代发出事件的对象,这里也就是button对象;EventArgs e 事件参数,可以理解为对事件的描述 ,它们可以统称为事件源。其中的代码逻辑,就是对事件的处理。我们可以统称为事件处理。 说了这么多,无非是想透过现象看本质:事件是由事件源和事件处理组成。 2.2. 发布订阅模式 定义对象间一种一对多的依赖关系,使得每当一个对象改变状态,则所有依赖于它的对象都会得到通知并被自动更新。 ——发布订阅模式 发布订阅模式主要有两个角色: 1,发布方(Publisher):也称为被观察者,当状态改变时负责通知所有订阅者。 2,订阅方(Subscriber):也称为观察者,订阅事件并对接收到的事件进行处理。 发布订阅模式有两种实现方式: 1,简单的实现方式:由Publisher维护一个订阅者列表,当状态改变时循环遍历列表通知订阅者。 2,委托的实现方式:由Publisher定义事件委托,Subscriber实现委托。 总的来说,发布订阅模式中有两个关键字,通知和更新。 被观察者状态改变通知观察者做出相应更新。 解决的是当对象改变时需要通知其他对象做出相应改变的问题。 如果画一个图来表示这个流程的画,图形应该是这样的: 3 实现发布订阅模式 相信通过上面的解释,对事件和发布订阅模式有了一个大概的印象。都说理论要与实践相结合,所以我们还是动动手指敲敲代码比较好。 我将以『观察者模式』来钓鱼这个例子为基础,通过重构的方式来完善一个更加通用的发布订阅模式。 先上代码: /// <summary > /// 鱼的品类枚举 /// </summary > public enum FishType { 鲫鱼, 鲤鱼, 黑鱼, 青鱼, 草鱼, 鲈鱼 } 钓鱼竿的实现: /// <summary > ///     鱼竿(被观察者) /// </summary > public class FishingRod { public delegate void FishingHandler(FishType type); //声明委托 public event FishingHandler FishingEvent; //声明事件 public void ThrowHook(FishingMan man) { Console.WriteLine("开始下钩!"); //用随机数模拟鱼咬钩,若随机数为偶数,则为鱼咬钩 if (new Random().Next() % 2 == 0) { var type = (FishType) new Random().Next(0, 5); Console.WriteLine("铃铛:叮叮叮,鱼儿咬钩了"); if (FishingEvent != null) FishingEvent(type); } } } 垂钓者: /// <summary > ///     垂钓者(观察者) /// </summary > public class FishingMan { public FishingMan(string name) { Name = name; } public string Name { get; set; } public int FishCount { get; set; } /// <summary > /// 垂钓者自然要有鱼竿啊 /// </summary > public FishingRod FishingRod { get; set; } public void Fishing() { this.FishingRod.ThrowHook(this); […]

龙生   07 Jun 2018
View Details
1 185 186 187 432