首页 文章 精选 留言 我的

精选列表

搜索[趋势探讨],共10000篇文章
优秀的个人博客,低调大师

mPaaS CodeDay#2 技术沙龙报名:支付宝移动端智能化能力构建与趋势探讨

【沙龙亮点】 当我们聚焦支付宝 App 构建高并发、高可用架构能力时,不难发现,在这背后隐藏着众多针对“自动化”及“智能化”能力的深度思考与落地实践。从“代码解析”、“路径规划”,再到“图像识别”,支付宝 App 将自然语言算法贴合具体的业务场景和挑战进行适宜的应用并帮助需求得以满足和发展。本期 CodeDay 将聚焦支付宝 App 如何逐步演进并发展“研发协同管理”、“无线实验集群”、“日志埋点分析”、“ABTest”等能力,从而满足日活量剧增的情况下,仍能保持稳定的交付质量、深度的用户洞察以及良好的用户体验。 【活动信息】 活动时间:2019 年 5 月 18 日(周六) 14:00-17:00活动地点:北京 - 中关村创业大街 氪空间免费报名:https://tech.antfin.com/activities/567?Info=

优秀的个人博客,低调大师

深入探讨HBASE

HBASE基础 1. HBase简介 HBase是一个高可靠、高性能、面向列的,主要用于海量结构化和半结构化数据存储的分布式key-value存储系统。它基于Google Bigtable开源实现,但二者有明显的区别:Google Bigtable基于GFS存储,通过MAPREDUCE处理存储的数据,通过chubby处理协同服务;而HBase底层存储基于hdfs,可以利用MapReduce、Spark等计算引擎处理其存储的数据,通过Zookeeper作为处理HBase集群协同服务。 2. HBase表结构 HBase以表的形式将数据最终存储的hdfs上,建表时无需指定表中字段,只需指定若干个列簇即可。插入数据时,指定任意多个列到指定的列簇中。通过行键、列簇、列和时间戳可以对数据进行快速定位。 2.1 行键(row key) HBase基于ro

优秀的个人博客,低调大师

探讨!到底什么是CDN?

如今这个移动互联网时代,越来越多的人使用手机观看视频,丰富自己的娱乐生活。 可是,大家在追剧的时候,有没有想过一个问题——为什么有时候明明自己的网速很快,但观看视频时,仍然卡顿? 回答这个问题之前,我们先来做一道算术题。 以之前很火的“延禧攻略”为例,当时曾经在某视频APP实现了1千万用户同时在线观看。 如果大家观看的是1080p清晰度的视频(理论上需要4Mbps带宽),那么,累计需要的流量带宽是10,000,000×4Mbps=40,000,000Mbps≈40Tbps。 对于优酷、爱奇艺这样的互联网视频内容提供商来说,这无疑是非常巨大的流量压力。 我们普通计算机的网卡,是1Gbps的带宽。如果是服务器,现在有10Gbps的网卡(万兆网卡)。 如果优酷有一台超级服务器,那么,这台超级服务器就需要4000块万兆网卡,而且必须百分之百跑满速度,才能够实现这1千万用户的流畅观看。 对于一些实力不够的服务商,或者突发流量陡增的情况,就会造成拥塞,从而导致卡顿和延时。 有这么一个说法:当用户打开一个页面,等待超过4秒,他就会关闭这个页面。也就是说,这个用户就会流失。 这应该是大家最讨厌的符号: 用户的流失,就意味着金钱的流失。没有任何一家互联网服务提供商希望这样的情况发生。所以,它们必须想方设法让自己的内容尽快呈现,缩短用户的等待时间,提升用户的体验。 而CDN,就是一项非常有效的缩短时延的技术。 CDN的诞生 上世纪80年代,互联网技术刚刚走入民用领域。 人们主要通过拨号来访问网络,带宽很低,用户也很少,所以,没有对骨干网以及服务器带来压力。 随着互联网的爆炸式发展,用户越来越多,加上宽带接入网的出现,内容源服务器和骨干网络的压力越来越大,无法及时响应用户的访问需求。 1995年,麻省理工学院教授、互联网的发明者之一,Tim Berners-Lee博士发现,网络拥塞越来越严重,将会成为互联网发展的最大障碍。 Tim Berners-Lee 于是,他提出一个学术难题,希望有人能发明一种全新的、从根本上解决问题的方法,来实现互联网内容的无拥塞分发。 当时Tim Berners-Lee博士的隔壁,是Tom Leighton教授的办公室。他是一位麻省理工学院应用数学教授。 Tom Leighton 他被Berners-Lee的挑战激起了兴趣,于是他请研究生Danny C. Lewin和其他几位顶级研究人员一起破解这个技术难题。 Danny C. Lewin 最终,他们开发了利用数学运算法则来处理内容的动态路由算法技术,有效地解决了这个难题。这个技术,就是CDN。 他们还为此专门成立了公司,发挥其商业价值。这个公司,就是后来鼎鼎大名的CDN服务鼻祖——Akamai公司。 CDN的原理 CDN这个技术其实说起来并不复杂。它最初的核心理念,就是将内容缓存在终端用户附近。 内容源不是远么?那么,我们就在靠近用户的地方,建一个缓存服务器,把远端的内容,复制一份,放在这里,不就OK了? 因为这项技术是把内容进行了分发,所以,它的名字就叫做CDN——Content Delivery Network,内容分发网络。 具体来说,CDN就是采用更多的缓存服务器(CDN边缘节点),布放在用户访问相对集中的地区或网络中。当用户访问网站时,利用全局负载技术,将用户的访问指向距离最近的缓存服务器上,由缓存服务器响应用户请求。(有点像电商的本地仓吧?) 大家可能觉得,这个不就是“镜像服务器”嘛?其实不一样。镜像服务器是源内容服务器的完整复制。而CDN,是部分内容的缓存,智能程度更高。 确切地说,CDN=更智能的镜像+缓存+流量导流。 而且还需要注意的是,CDN并不是只能缓存视频内容,它还可以对网站的静态资源(例如各类型图片、html、css、js等)进行分发,对移动应用APP的静态内容(例如安装包apk文件、APP内的图片视频等)进行分发。 我们来举个例子,看看CDN的具体工作流程。 如果某个用户想要访问优酷的视频点播内容,那么: 具体步骤: ①、当用户点击APP上的内容,APP会根据URL地址去本地DNS(域名解析系统)寻求IP地址解析。 ②、本地DNS系统会将域名的解析权交给CDN专用DNS服务器。 ③、CDN专用DNS服务器,将CDN的全局负载均衡设备IP地址返回用户。 ④、用户向CDN的负载均衡设备发起内容URL访问请求。 ⑤、CDN负载均衡设备根据用户IP地址,以及用户请求的内容URL,选择一台用户所属区域的缓存服务器。 ⑥、负载均衡设备告诉用户这台缓存服务器的IP地址,让用户向所选择的缓存服务器发起请求。 ⑦、用户向缓存服务器发起请求,缓存服务器响应用户请求,将用户所需内容传送到用户终端。 ⑧、如果这台缓存服务器上并没有用户想要的内容,那么这台缓存服务器就要网站的源服务器请求内容。 ⑨、源服务器返回内容给缓存服务器,缓存服务器发给用户,并根据用户自定义的缓存策略,判断要不要把内容缓存到缓存服务器上。 CDN的好处 采用CDN技术,最大的好处,就是加速了内容的访问——用户与内容之间的物理距离缩短,用户的等待时间也得以缩短。 而且,分发至不同线路的缓存服务器,也让跨运营商之间的访问得以加速。 例如中国移动手机用户访问中国电信网络的内容源,可以通过在中国移动架设CDN服务器,进行加速。效果是非常明显的。 此外,CDN还有安全方面的好处。内容进行分发后,源服务器的IP被隐藏,受到攻击的概率会大幅下降。而且,当某个服务器故障时,系统会调用临近的健康服务器 进行服务,避免对用户造成影响。 正因为CDN的好处很多,所以,目前所有主流的互联网服务提供商,都采用了CDN技术。所有的云服务提供商,也都提供了CDN服务(价格也不算贵,按流量计费)。 某某云的CDN服务 CDN的弱点 CDN虽然有很多的优点,但它并不是万能的。在部分场景下,CDN并不是适用。 首先,CDN适用于静态的内容,不适用动态的内容。用户动态的实时交互数据,是难以缓存的。例如一些频繁修改的数据库表单内容等。(大家可能没想到,直播其实也是可以使用CDN的。感兴趣的同学可以搜一下“直播CDN”。) 其次,很多应用提供商和内容服务商,为了保护自身的数据私密,不允许第三方公司CDN缓存他们的数据,只允许自家CDN缓存自家的数据。这个对用户体验会造成一定影响。 第三,建设CDN意味着不菲的资金投入。不管是自己买服务器搭建CDN,还是租用云服务提供商的CDN服务,都需要花钱。而且,区域越多,花的钱越多。这些CDN到底有没有人用,利用率是多少,很难精准预测。也许大部分时间里,利用率很低,就造成了资源浪费。 CDN和通信 CDN是从传统IT行业发展起来的一项服务。但是,对于我们通信行业来说,CDN也有非常大的商业价值。 互联网服务提供商采用CDN,是以存储换时延。花钱购置CDN服务器或云计算服务,以此换取更好的用户体验。 通信运营商也追捧CDN,但它们的目的,是以存储换带宽——通过服务“下沉”,减轻上层骨干网络的流量压力,避免硬件扩容,降低网络建设成本。 这个很好理解啊,如果大量的业务流量数据在骨干网跑来跑去,骨干网肯定吃不消,要拼命扩容。如果这些业务流量数据在底层就被解决了,那么,骨干网的带宽压力自然就减轻了。不是么? 很多运营商已经将CDN下沉到地市级,以此减轻压力,同时可以提升用户体验。 讲到这里,广大通信汪们是不是想到了什么? 没错,这个和现在非常热门的移动边缘计算,有异曲同工之妙。 一直以来,随着网络能力的不断提升,内容资源和计算能力都在不断“往上走”,走到云计算中心。由一个核心云计算中心,对所有终端节点提供服务。 结果,人们回过头来发现,对于非常大的面积区域,非常多的用户数量,尤其是国家级或世界级的服务,不管你把这个中心设在哪里,也不管你这个中心的能力有多强大,都无法克服物理距离上的障碍,会导致无法忍受的延时和网络拥塞。 于是乎,人们就开始把云计算中心进行部分“下沉”,这才有了雾计算、霾计算。甚至人们开始质疑,集中式计算是否会最终被分布式计算所取代? 区块链,就是分布式计算的代表 在小枣君看来,不存在谁完全取代谁的问题。不同的场景带来不同的需求,不同的需求需要不同的网络架构。场景的多样化是现实存在的,所以,网络架构的灵活化,也是必然的选择。 CDN和边缘计算到底是什么关系呢? 其实,我个人认为,CDN可以算是边缘计算的一种特殊形式。CDN主要是存储能力和少部分计算能力的下沉,功能较为有限。真正的MEC边缘计算,能力更强大,功能更全面,更加偏向算力下沉,而非内容下沉。 好啦,以上就是关于CDN的介绍,希望对大家有所帮助!感谢大家的耐心阅读,我们下期再见!

优秀的个人博客,低调大师

探讨缓存行与伪共享

最近项目中有个需求,需要用到有界队列对访问请求量进行流量削峰请求,同时作为一个缓冲层对请求处理进行后续处理,Java 内置有界队列 ArrayBlockingQueue 可以满足这方面的需求,但是性能上并不满足,于是使用了 Disruptor,它是英国外汇交易公司 LMAX 开发的一个高性能队列,了解到它内部解决伪共享问题,今天就和大家一起学习缓存行与伪共享相关的知识。 缓存行(Cache line) 对计算机组成原理相对熟悉的小伙伴都知道,CPU 的速度比内存的速度高了几个数量级,为了 CPU 更快从内存中读取数据,设置了多级缓存机制,如下图所示: 当 CPU 运算时,首先会从 L1 缓存查找所需要的数据,如果没有找到,再去 L2 缓存中去找,以此类推,直到从内存中获取数据,这也就意味着,越长的调用链,所耗费的执行时间也越长。那是不是可以从主内存拿数据的时候,顺便多拿一些呢?这样就可以避免频繁从主内存中获取数据了。聪明的计算机科学家已经想到了这个法子,这就是缓存行的由来。缓存是由多个缓存行组成的,而每个缓存行大小通常来说,大小为 64 字节,并且每个缓存行有效地引用主内存中的一块儿地址,CPU 每次从主内存中获取数据时,会将相邻的数据也一同拉取到缓存行中,这样当 CPU 执行运算时,就大大减少了与主内存的交互。 下面我用一个例子让大家体会一下用缓存行和不用缓存行在性能上的差异: //以下源码例子来源:https://tech.meituan.com/2016/11/18/disruptor.htmlpublicclassCacheLineEffect{//考虑一般缓存行大小是64字节,一个long类型占8字节staticlong[][]arr;publicstaticvoidmain(String[]args){intsize=1024*1024;arr=newlong[size][];for(inti=0;i<size;i++){arr[i]=newlong[8];for(intj=0;j<8;j++){arr[i][j]=0L;}}longsum=0L;longmarked=System.currentTimeMillis();for(inti=0;i<size;i++){for(intj=0;j<8;j++){sum=arr[i][j];}}System.out.println("[cacheline]Looptimes:"+(System.currentTimeMillis()-marked)+"ms");marked=System.currentTimeMillis();for(inti=0;i<8;i+=1){for(intj=0;j<size;j++){sum=arr[j][i];}}System.out.println("[nocacheline]Looptimes:"+(System.currentTimeMillis()-marked)+"ms");}} 我使用的测试运行环境配置如下: 运行后结果如下: 可以看到,使用缓存行比没有使用缓存行的性能提升了将近 4 倍。 伪共享问题 当 CPU 执行完后,还需要将数据回写到内存上,以便于别的线程可以从主内存中获取最新的数据。假设两个线程都加载了相同的 Cache line 数据,会产生什么样的影响呢?下面我用一张图解释: 数据 A、B、C 被加载到同一个 Cache line,假设线程 1 在 core1 中修改 A,线程 2 在 core2 中修改 B。 线程 1 首先对 A 进行修改,这时 core1 会告知其它 CPU 核,当前引用同一地址的 Cache line 已经无效,随后 core2 发起修改 B,会导致 core1 将数据回写到主内存中,core2 这时会重新从主内存中读取该 Cache line 数据。 可见,如果同一个 Cache line 的内容被多个线程读取,就会产生相互竞争,频繁回写主内存,降低了性能。 如何解决伪共享问题 要解决伪共享这个问题最简单的做法就是将线程间共享元素分开到不同的 Cache line 中,这种做法叫用空间换取时间,具体做法如下: publicfinalstaticclassValuePadding{//前置填充对象protectedlongp1,p2,p3,p4,p5,p6,p7;//value值protectedvolatilelongvalue=0L;//后置填充对象protectedlongp9,p10,p11,p12,p13,p14,p15;} JDK1.8 有专门的注解 @Contended 来避免伪共享,为了更加直观,我使用了对象填充的方法,其中 protected long p1, p2, p3, p4, p5, p6, p7 作为前置填充对象,protected long p9, p10, p11, p12, p13, p14, p15作为后置填充对象,这样任意线程访问 ValuePadding 时,value 都处于不同的 Cache line 中,不会产生伪共享问题。 下面的例子用来演示伪共享与解决伪共享后的性能差异: publicclassMyFalseSharing{publicstaticvoidmain(String[]args)throwsInterruptedException{for(inti=1;i<10;i++){System.gc();finallongstart=System.currentTimeMillis();runTest(Type.PADDING,i);System.out.println("[PADDING]Threadnum"+i+"duration="+(System.currentTimeMillis()-start));}for(inti=1;i<10;i++){System.gc();finallongstart=System.currentTimeMillis();runTest(Type.NO_PADDING,i);System.out.println("[NO_PADDING]Threadnum"+i+"duration="+(System.currentTimeMillis()-start));}}privatestaticvoidrunTest(Typetype,intNUM_THREADS)throwsInterruptedException{Thread[]threads=newThread[NUM_THREADS];switch(type){casePADDING:DataPadding.longs=newValuePadding[NUM_THREADS];for(inti=0;i<DataPadding.longs.length;i++){DataPadding.longs[i]=newValuePadding();}break;caseNO_PADDING:Data.longs=newValueNoPadding[NUM_THREADS];for(inti=0;i<Data.longs.length;i++){Data.longs[i]=newValueNoPadding();}break;}for(inti=0;i<threads.length;i++){threads[i]=newThread(newFalseSharing(type,i));}for(Threadt:threads){t.start();}for(Threadt:threads){t.join();}}//线程执行单元staticclassFalseSharingimplementsRunnable{publicfinalstaticlongITERATIONS=500L*1000L*100L;privateintarrayIndex;privateTypetype;publicFalseSharing(Typetype,finalintarrayIndex){this.arrayIndex=arrayIndex;this.type=type;}publicvoidrun(){longi=ITERATIONS+1;//读取共享变量中指定的下标对象,并对其value变量不断修改//由于每次读取数据都会写入缓存行,如果线程间有共享的缓存行数据,就会导致伪共享问题发生//如果对象已填充,那么线程每次读取到缓存行中的对象就不会产生伪共享问题switch(type){caseNO_PADDING:while(0!=--i){Data.longs[arrayIndex].value=0L;}break;casePADDING:while(0!=--i){DataPadding.longs[arrayIndex].value=0L;}break;}}}//线程间贡献的数据publicfinalstaticclassData{publicstaticValueNoPadding[]longs;}publicfinalstaticclassDataPadding{publicstaticValuePadding[]longs;}//使用填充对象publicfinalstaticclassValuePadding{//前置填充对象protectedlongp1,p2,p3,p4,p5,p6;//value值protectedvolatilelongvalue=0L;//后置填充对象protectedlongp9,p10,p11,p12,p13,p14,p15;}//不填充对象//@sun.misc.ContendedpublicfinalstaticclassValueNoPadding{protectedvolatilelongvalue=0L;}enumType{NO_PADDING,PADDING}} 运行程序,测试结果如下: 可见,当有多个线程同时操作同一个 Cache line 的数据时,伪共享问题会影响 CPU 性能。 近期热文 Seata RPC 模块的重构之路 从源码和日志文件结构中分析 Kafka 重启失败事件 记一次 Kafka 重启失败问题排查 图解:Kafka 水印备份机制 记一次 Kafka 集群线上扩容 Kafka重平衡机制 Seata 配置中心实现原理 Seata AT 模式启动源码分析 分布式事务中间件 Seata 的设计原理 我对支付平台架构设计的一些思考 聊聊 Tomcat 的架构设计 关于 Kafka 的一些面试题目 基于Jenkins Pipeline自动化部署 RocketMQ消息发送的高可用设计 深度解析RocketMQ Topic的创建机制 mybatis-plus 源码分析之sql注入器 Mybatis源码分析之Mapper注册与绑定 从源码的角度解析线程池运行原理 关于线程池你不得不知道的一些设置 你都理解创建线程池的参数吗? Java并发之AQS源码分析(二) Java并发之AQS源码分析(一) 本文分享自微信公众号 - 后端进阶(objcoding)。如有侵权,请联系 support@oschina.cn 删除。本文参与“OSC源创计划”,欢迎正在阅读的你也加入,一起分享。

优秀的个人博客,低调大师

深入探讨LSM Compaction机制

compaction策略 compaction的主要作用是数据的gc和归并排序,是lsm-tree系统正常运转必须要做的操作,但是compaction任务运行期间会带来很大的资源开销,压缩/解压缩、数据拷贝和compare消耗大量cpu,读写数据引起disk I/O。compaction策略约束了lsm-tree的形状,决定哪些文件需要合并、任务的大小和触发的条件,不同的策略对读写放大、空间放大和临时空间的大小有不同的影响,一般系统会支持不同的策略并配有多个调整参数,可根据不同的应用场景选取更合适的方式。 基础概念 读放大 每次读请求带来的读盘次数 写放大 每写1byte数据带来n bytes的数据写盘,写放大为n。本质上写放大需要跟全局有序做权衡,对序要求越高的系统写放大就会越严重,B-Tree系列是随时有序的代表,写放大也更为严重,而LS

优秀的个人博客,低调大师

关于 mybatis 和 orm 区别与探讨!!!

mybatis-mp是一款优秀的ORM框架,官方文档:http://mybatis-mp.cn!!! 网上有很多人 对于以下3个问题 非常有争议: 1:很多人认为mybatis是ORM框架,经常和其他ORM框架一起比较 2:很多认为直接写xml 里写sql 更好 灵活度更高,容易修改;所以 都不想用ORM框架;认为ORM 可读性不高,还不好修改;甚至有人认为ORM框架的代码是硬编码 3:很多认为单表就足够了,不需要join,join 查询性能差,所以 不准使用join 所以你们的观点呢? 评论区见真章,写下你们的观点 !!!

优秀的个人博客,低调大师

开源软件商业模式的探讨

声明:我们的开源项目“ Milvus 向量搜索引擎”还处在社会主义初级阶段。以下内容是我们目前对开源工作的摸索,并非最佳实践。 开源许可证 既然我们决定了要开源,第一步便是要选择合适的开源许可证。虽然自由软件创始人 RMS 曾经倡导 Copyleft 概念,但 Copyleft 也是一种特殊的 Copyright 。 那么,什么是开源许可证?简单来说,一个许可证只要经过 OSI ( Open Source Initiative )认证,就可以被称之为开源许可证。 OSI 有专门的流程来审核一个许可证是否符合开源定义( Open Source Definition )。比如说, MongoDB 新设计的 SSPL ( Sever Side Public License )在完成 OSI 认证之前, MongoDB 只能说自己的许可证是源码可用( source available ),而不能说自己是开源(当然,这个限制属于行业惯例,没有强制性)。 目前主流的开源许可证,可以在 OSI 网站上查询到。网上也有很多文章去比较各个许可证之间的不同(可参考阮一峰老师的博客),我就不一一赘述了。这里主要结合我们的自身情况来谈一下开源许可证的选择。开源许可证简单来说,可以分为三档: 严格,以 GPL 2.0 许可证为代表,典型软件是 MySQL 适中,以 Apache 2.0 许可证为代表,目前使用最广泛 宽松,以 BSD,MIT , PostgreSQL 许可证为代表,典型软件是 PostgreSQL 熟悉数据库的朋友一定知道 MySQL 和 PostgreSQL 。 MySQL 是最流行的开源数据库,但 PostgreSQL 是衍生项目最多的开源数据库。现在的新项目很少使用 GPL 2.0 许可证,它的传染性应该是大家最有顾虑的地方。 对于推广基础技术来说,MIT/BSD 类的许可证是一个好选择。可能现在已经很少人使用 FreeBSD 。但它也还在不断的发展,因为采用非常宽松的 2-Clause-BSD 许可证, FreeBSD 被不少厂商用来开发自己的闭源系统。比如, Sony 的 Play Station 3 和 4 的系统都基于 FreeBSD , 还有任天堂的 Swtich 游戏机也是。 Redis 也采用宽松的 3-Clause-BSD 许可证(相比 2-Clause 多了对商标的使用限制)。不过, Redis 整个工具链的许可证情况十分复杂。以至于当 Redis 切换部分组件的许可证时,引起了业界很大的误解。因此中途将许可证变严格是件有点敏感的事情。 看起来颇为复杂的 Redis 许可矩阵。 如果上策太急,下策太缓。那么就选择中间的 Apache 2.0 。Apache 2.0 目前是 Apache 基金会与 CNCF 基金会推荐的默认开源许可证。 Github 网站对 Apache 2.0 许可证的简易说明 Apache 2.0 像其他开源许可证一样不限制商业使用,专利授权也默认包含其中。不过 Apache 2.0 也明确规定了在此开源许可证下软件厂商的免责条款。这也就是开源软件公司提供订阅增值服务的法律基础。 不过即使是 Apache 2.0 这么成熟的开源许可证,大家还是有一个担心:公有云。 需要防范公有云厂商吗 开源软件与公有云的关系这两年有点紧张,一个比较流行的观点是公有云插管吸血开源软件,而对开源社区没有太多贡献。不少开源项目开始寻找在公有云面前保护自己的方法。毕竟公有云的出现,一定程度上打乱了原有的开源商业模式。最终用户通过购买云服务,从公有云服务商那里的到了保障,开源厂商被绕开了。 于是, Common Clause 应运而生。 Common Clause 是一种附加条款,开源厂商依然需要选择一个基本的主许可证。最终的形式类似: Apache 2.0 + Common Clause 1.0 。 Common Clause 比较精炼,全文只有 3 句话,如下: The Software is provided to you by the Licensor under the License, as defined below, subject to the following condition. Without limiting other conditions in the License, the grant of rights under the License will not include, and the License does not grant to you, the right to Sell the Software. For purposes of the foregoing, "Sell" means practicing any or all of the rights granted to you under the License to provide to third parties, for a fee or other consideration (including without limitation fees for hosting or consulting/ support services related to the Software), a product or service whose value derives, entirely or substantially, from the functionality of the Software. Any license notice or attribution required by the License must also include this Commons Clause License Condition notice. Common Clause 主要禁止他人在不增加开源软件价值的情况下,利用开源软件牟利。它的限制性主要体现在以下三点: 禁止他人 对软件生态构建的影响 利用原软件进行 license 销售 非常小。目前主流观点是开源软件不收取 license 费用,软件收费以按年支付的订阅模式进行。 提供软件支持服务 比较小。尤其是产品初期,大家都不了解,需要依靠官方支持。官方提供订阅模式,大家比较容易接受。产品的订阅收费模式能够得到保障。不过将来等产品成熟以后,需要考虑参照 Oracle 的 OCP 方式,提供一些针对专业人士的产品能力认证,以缓和这一点可能的影响。 提供软件托管服务 防范云厂商。限制云厂商不能通过托管云服务( hosting )的方式,利用原软件进行盈利。但不代表用户不能在云环境里使用该软件。Apache 2.0 + Common Clause 1.0 不会限制用户运行软件的硬件环境,只要用户购买订阅服务,产品方一样会提供支持服务。 假设第三方在开源软件的基础上构建了一整套面向用户的应用,这套新应用增加了原开源软件的价值,那么这套新应用不会受到任何限制。这一点保证了开源厂商与合作伙伴之间的合作关系不会受到影响。 不过 Common Clause 没有经过 OSI 认证,因此添加了 Common Clause 以后建议只说自己是源码可用( source available )。虽然会引起一定的争议,不过初创开源项目选择添加 Common Clause 看起来正受到越来越多人的理解。 然而,我们的开源项目并不打算加上 Common Clause 。有两个重要的原因。 MongoDB 的启示 MongoDB 是开源项目成功的范例。 MongoDB 一开始就采用 AGPL 3.0 许可证。如果公有云要利用 MongoDB 提供服务,那么公有云厂商需要公布相关底层服务的源码。因此, AWS , Azure, Google Cloud 等一众美国公有云都选择自行开发文档型数据库。而在美国以外, MongoDB 却很难用法律武器保护自己。 2018 年 10 月 MongoDB 修改新版本的许可证时,再次抱怨了公有云厂商对 MongoDB 利益的侵害,主要指的就是美国以外的公有云厂商。因此,志在全球的开源基础软件厂商其实很难仅靠一个许可证来对自己进行全面的保护。 另一方面,当 AWS 有了 DynamoDB ; Azure 有了 Cosmos DB ; Google Cloud 有了 Cloud Firestore 之后,文档数据库不再是 MongoDB 一家独大。在之后的移动互联网浪潮中,移动端的 MongoDB Mobile 没有达到期待中的影响力。毕竟 Realm 这样的移动端文档数据库可以直接和多个公有云文档数据库同步,极大的方便了移动开发者。2019 年 4 月, MongoDB 以 3900 万美元收购了 Realm 。 防范别人的同时也部分影响了自己的发展空间,是否值得?答案因人而异,开源项目需要结合自身情况作出一个选择。 四爷的新策略 据咨询公司 Gartner 的统计, Google Cloud 2018 年占据公有云 IaaS 市场 4.0% 的份额,排行全球第四。依然不及老大 AWS 市场占有率( 47.8% )的一个零头。 Google Cloud 想迎头赶上,他该怎么办? 在今年的 Google Cloud Next 大会上,新上任的 Google Cloud CEO 一举请来了 Redis Lab CEO 与 MongoDB CEO 帮忙站台。大会上 Google Cloud 推出了 Redis 的托管服务, MongoDB 上了 Google Cloud Marketplace 。后续 MongoDB 的 Atlas 云服务还和 Google Cloud 展开了一系列合作。 Redis 和 MongoDB 在开源界与互联网行业有较大的技术影响力。而且他们是开源界对公有云厂商开炮比较多的两家。近期他们又先后针对公有云厂商修改了自己的许可证。因此 Google Cloud Next 大会上传达的信息很有意思。 与成熟的开源厂商合作,看起来正是 Google Cloud 的新策略。这条路值得一试。毕竟,老四恐怕很难用老大的方法来战胜老大。 “学我者生,似我者死。” —— 齐白石 Google Cloud 第一个想明白了。我相信会有越来越多的公有云厂商想明白这个问题,选择与成熟的开源厂商合作。所以对开源基础软件来说,当务之急是提升自身的成熟度,防范之心可以暂时放到一边。 商业设计 在上一篇文中,我们提到“ Apache 基金会拥有 1.9 亿行代码。根据 COCOMO II 模型估算,这些代码的开发成本超过 200 亿美元( 2019 年报)。”如此算来,每一行代码的开发成本超过 200 美元。所以千万别觉得开源软件就该免费使用。 典型的开源商业模式 目前比较成熟的开源软件商业模式有以下几种: 订阅服务:开源许可证免除了厂商对软件质量与软件缺陷修复的责任。而这些都是企业级应用所必须的。因此,最自然的商业模式就是提供软件订阅服务,从而向用户提供生产级的服务支持响应和 hotfix 修复。 高级功能:比如 Redis 。核心部分的组件是开源的。但工具类软件,进阶功能(如多租户,无共享分布式架构等)都是收费的。 云服务:比如 Databricks 。 Spark 是开源的,但收费版本仅提供 Azure 和 AWS 上的云服务。 生态收益(仅限超大型开源厂商):比如据华尔街分析师估算 Google 每年要支付近百亿美元给 Apple ,就为了 iPhone 上的默认搜索引擎入口。想想 Android 帮 Google 省了多少钱? 软件世界里有两个重大难题:一是大型软件系统的项目管理(人月神话),另一个是软件定价。关于项目管理,已经有了不少的研究与实践,大家多少有个参照物。而软件定价没有什么成熟的公式与模型。 但至少对于开源软件的定价,要避开下面两个坑: 定高价,打 1 折 不采用订阅模式 这些都是传统商业软件的模式。传统商业软件提供给客户的是资产,开源软件提供给用户的是服务。 如果大型用户要求对软件进行买断怎么办?大型用户倾向于一次性付费,并不是他们喜欢购买一堆软件资产。背后的原因在于大型用户内部的软硬件采购流程,需要采购人员与 IT 技术人员共同介入。而采购并不是技术人员的本职工作,以及事后的各种审计。因此技术人员更喜欢一次性买断,以省去未来的麻烦。请提醒他们,开源软件提供的是服务,服务是不能买断的,应该走更便捷的服务采购流程。 向 AWS 学习 基础软件的商业化是件很有挑战的事情。好在有很多成熟的企业可供我们参考。如果说 Oracle 是必须研究的传统商业软件公司,那么 AWS 毫无疑问就是必须好好学习的云服务公司。 刚才说软件定价没有什么成熟的公式与模型?其实 AWS 帮大家摸索了一个公有云上软件的定价方式。AWS Aurora 数据库据称是 AWS 上增长最快最赚钱的云服务。 Aurora 在技术上是非常创新的云原生数据库,带出了一众追随者。依据官方宣传: Amazon Aurora 的速度最高可以达到标准 MySQL 数据库的五倍、标准 PostgreSQL 数据库的三倍。它可以实现商用数据库的安全性、可用性和可靠性,而成本只有商用数据库的 1/10。(引用自 https://aws.amazon.com/cn/rds/aurora/ ) 那么这样一款技术如此先进的云上数据库是怎么定价的呢?以下对比 Aurora MySQL 所有可选的实例规格与 RDS MySQL 之间的定价: 云实例规格 RDS MySQL Aurora MySQL Aurora 溢价 db.t3.small 0.034 0.041 20.59% db.t3.medium 0.068 0.082 20.59% db.t2.small 0.034 0.041 20.59% db.t2.medium 0.068 0.082 20.59% db.r5.large 0.24 0.29 20.83% db.r5.xlarge 0.48 0.58 20.83% db.r5.2xlarge 0.96 1.16 20.83% db.r5.4xlarge 1.92 2.32 20.83% db.r5.12xlarge 5.76 6.96 20.83% db.r4.large 0.24 0.29 20.83% db.r4.xlarge 0.48 0.58 20.83% db.r4.2xlarge 0.96 1.16 20.83% db.r4.4xlarge 1.92 2.32 20.83% db.r4.8xlarge 3.84 4.64 20.83% db.r4.16xlarge 7.68 9.28 20.83% 单位:美元/小时 当然 Aurora MySQL 和 RDS MySQL 的技术实现不太一样,同样实例规格需要的硬件也不能简单划上等号。不过考虑到 AWS 本身的体量,两者间硬件差异的成本应该是微乎其微的。可以大致认为 20% 的溢价来自 Aurora MySQL 软件。 基础软件上公有云 Marketplace 的时候怎么定价,总算有个参照物了。 后记 虽然写了两篇文章,但也只是涉及了开源的一小部分。开源模式可一点也不比传统商业软件的模式要简单。 其中比较关键的社区运营和开发者生态构建,我们也还在不断的摸索。等有一天我们形成自己的方法与风格,届时一定与大家分享。希望国内的基础软件同行都能一起进步。

资源下载

更多资源
腾讯云软件源

腾讯云软件源

为解决软件依赖安装时官方源访问速度慢的问题,腾讯云为一些软件搭建了缓存服务。您可以通过使用腾讯云软件源站来提升依赖包的安装速度。为了方便用户自由搭建服务架构,目前腾讯云软件源站支持公网访问和内网访问。

Spring

Spring

Spring框架(Spring Framework)是由Rod Johnson于2002年提出的开源Java企业级应用框架,旨在通过使用JavaBean替代传统EJB实现方式降低企业级编程开发的复杂性。该框架基于简单性、可测试性和松耦合性设计理念,提供核心容器、应用上下文、数据访问集成等模块,支持整合Hibernate、Struts等第三方框架,其适用范围不仅限于服务器端开发,绝大多数Java应用均可从中受益。

Rocky Linux

Rocky Linux

Rocky Linux(中文名:洛基)是由Gregory Kurtzer于2020年12月发起的企业级Linux发行版,作为CentOS稳定版停止维护后与RHEL(Red Hat Enterprise Linux)完全兼容的开源替代方案,由社区拥有并管理,支持x86_64、aarch64等架构。其通过重新编译RHEL源代码提供长期稳定性,采用模块化包装和SELinux安全架构,默认包含GNOME桌面环境及XFS文件系统,支持十年生命周期更新。

WebStorm

WebStorm

WebStorm 是jetbrains公司旗下一款JavaScript 开发工具。目前已经被广大中国JS开发者誉为“Web前端开发神器”、“最强大的HTML5编辑器”、“最智能的JavaScript IDE”等。与IntelliJ IDEA同源,继承了IntelliJ IDEA强大的JS部分的功能。

用户登录
用户注册