Silence & Solitude makes...

Pu's mind space

去国行

7月底离职了,待业的这些日子我抽空回去老家住了几天–自打学生时代以后就没有住过这么久了。我这趟回去是为了出国而道别,当然也要向亲友们解释为什么要出去这个问题。但是一如既往地,日子在觥筹交错,醉而复醒中过去了,又加上谈离别这样的事情,笑泪交织地,并没有能把这个问题回答清楚。所以回宁之后想着写这么一篇文字,题目来自拜伦的短诗,内容却并非诗中的决绝豪迈。

工作之前的我从来没有想过要出国,出国的想法是工作和安家之后的这几年才产生的,是一系列经历和感受之后的结果。前30年你们是看着我成长的–那些幸福的时光,我的记忆力很好,会永远记得那些点滴–你们对于从前的我的了解也是真切的。但当今中国的发展日新月异,节奏也越来越快,几年里出现的新事物足够淘汰一批保守者。爷爷年岁大了,前些年终于学会了自己用手机的通讯录打电话发短信等,可是孩子们突然就都用微信了,智能机+微信的复杂度对他来说是无法掌控了,只能放弃日常交流几个月才打一次电话,时代的向前就是这么残酷。而我自己在个人发展的道路上自私地冲了几年,带给亲人的就是无法理解,甚至基本观念上的割裂。虽然难度很大,我还是希望挑几点说一下,讲下这几年我是怎么从你们了解的那个人走到现在的,期望得到你们的理解。

工作性质

我是程序员。如果这篇文章不是为我的亲人们所写,那第一部分就已经可以结束了。因为干这行的都知道,程序员”想“出去,”能“出去。
首先,想出去。为什么?
国内程序员996的工作状态(从早上9点上班到晚上9点,一周工作6天),圈外应该也都知道了,而我因为在号称美国国企的Oracle待过几年,了解国外同事的工作状态,只能叹息我们确实是发展中不得不拼。事实上对于996的抱怨不仅是工作时长本身,而是管理方式上不尊重法不尊重人,这是更根深蒂固的。
职业发展上,比起快速把自己的技术快速变现,我更倾向继续积累和钻研。单纯的技术发展,虽然国内条件也很不错,但是不得不说,大部分的原始干货技术创新还是在外面,阿里云王坚博士也说“外面一开源,我们就有技术创新”。同时因为英语与计算机语言的关联比中文这种象形文字更容易发生,所以大部分的技术文档还是英文的更精确(这个因为所以的关联乍看有点牵强,以后有空可以展开一下这个话题)。这就要求程序员懂英语用英语,哪怕仅仅是看技术文档,自然而然容易因为熟悉语言转向了解文化和了解国外的生活等等。
其次,能出去。
刚才说了程序员通常对英语有要求,好的程序员一大部分英语能力也不低。
另外,不像是法务工作者或者公务员,其职业能力是和某个政体或者地域绑定的,程序员的职业能力天然就是全球性的。甲骨文裁员的时候部分美国同事客气地说,希望以后还有机会继续共事,我意识到我是能出去的。

生活状态

之前写过一个关于黑龙江大马哈鱼的文章,一到秋天,性成熟的大马哈鱼就会洄游,从大海沿江,沿着河,沿着溪,一路回到生他们的石滩上,在平静的石头和枯木下面产卵,然后死亡或成为熊的食物。为了后代能生在平静的一汪清水中,即使肚皮磨破,或者被熊掌拍晕也毅然决然千里洄游,是什么驱动了它们这样的行为?大自然真是一个奇妙的东西,人也不例外。我也不知道是被什么激素刺激着,总之就感觉到了30岁之后关于孩子的考虑就开始折磨我了:原来住的好好的小区,现在看到路上玩耍孩子和行驶的汽车离得不到20cm,我就感觉这里没法呆;原来向往的人车分流的郊区新小区,发现晚上的渣土车队和白天的装修声浪,就觉得这里没法呆;原来生活得好好的中国,看到四川还是哪儿一个乖戾男子摔小孩的视频我就觉得这里没法呆。从前在公共场合跟人流斗得不亦乐乎,现在逛博物馆,看到小孩吵到了人群,我就会想我以后该怎么处理这样的局面,因为吵闹是孩子的天性我管不了,人群里有没有乖戾的人我也控制不了,我只能去一个没有拥挤人群的博物馆带孩子玩了,毕竟如果只有几个人,孩子挥舞的手不会打到人,没有长长的队人们也不会因为急切而暴躁。
我知道国内很多小孩过得很好,以后也有很好的发展,上述的想法只是我自己作为程序员吹毛求疵惯了带来的观念问题,可能跟孟母三迁有点类似的意思吧。总之30多岁开始想要要孩子了我就开始思考各种解决办法,一开始想的是去杭州认真干几年多赚钱,后来真的觉得钱的数量没有几个量级的改变的话(而我也不可能做到),还是解决不了大国情带来的问题。这个大国情就是中国在快速发展,用发展解决发展中的问题,中年人忙到没法照顾老年人和孩子。可能温州动车事故给高铁事业带来了很多的教训也暴露了不少问题,这些教训和问题真的让高铁发展得更好了,可是那些生命也只是作为野蛮发展中的问题被解决掉就没有了,剩下的人因为生命的离开而叹息了几天之后又开始为高铁出国而久久地唱起赞歌。大的环境没有对错,落后过挨打过就应该努力发展,只是对于我这个个体,我不是有侵略性的人,如果只有一将和万骨,我大概率是在那堆骨头里。见过父辈在下岗潮中的无奈,听过祖辈在wg里的荒诞,到了我们自己该走的路,与其打着鸡血等待玄幻,不如压住愤青之气心怀悲悯远远旁看。可是根终究是丢不掉的,我还是会回来的。

Thoughs on Chum Salmons

Small Salmon

It’s the first time I write an article expressing subtle feelings in English. Though I have written some English articles before, it’s basically used to describe things more definitely or more professionally. And I know I can only vaguely express feelings with this language, so just like Leonardo’s reverse scripts, using my Chinglish to write an article is kind of trying to encrypt it. So I won’t blame if you were scared away by the 6 (maybe more) grammar errors appearing in this first paragraph.

Starting with an introduction to a specific kind of fish. The “Chum Salmon” in title, “Oncorhynchus keta” as the biological terminology, is a kind of migratory fish, which born at rocky small streams in cold zones in Northen US or North Asia, as the title picture shows. Typically their birth day is in Spring, latter when their first summer comes, they will swim along streams to rivers and finally to the Pacific and live their for arround 3 years, which is almost their whole life. After that they will go up along the rivers to streams, some place where they are born, to spawn there.

Spawning Salmon

This is amazing. I wonder if biologiests know how this happends, how such instinct is composed of. Do they achieve this by following routes in their memories, with the help of some build-in high resolution GPS system, or are they driven by some kind of hormone whoes secretion is highly and sentitively connected with temporature, fluid speed, and clearity of wator. What will happen to a group which is born in a specific stream and reclaim land from the stream when that group/generation of Chum Salmons are in ocean? Will they still heading to that the exact spot or will they went to similar places? Will they still spawn if they can’t find a place which is similar to the environment they stored in their childhood memory?

This is not another article but, my wife is 32 years old, me too. The world has experienced huge changes in this 32 years, even more in China. Old generations always try to help young generation with their experience on living, even though they use web and cars heavily, they think their experiences about making a living, about building a harmony family, about giving birth to child, about pregnancy-care should be the same, or more or less reusable. As the most responsible generation of this society, 30+s should be cruel neither to elders nor the youth. But if elders regard 30+s to have children as their source of happiness, there’s something cruel going to happen.

I feel driven by some instinction, though haven decided not to give birth to chidren in recent 2 years last year, I can’t stop keeping thinking of it. How to name such instinct? Like protecting next generation even before they are really exist? How can I consider to protect an not existing thing(child)? Just like I can’t picture wave-particle duality of light. I feel like being a Salmon going up the rivers, difference is I don’t exactly know where the stream is. Maybe just following distinct will make things easier, but it would be the last option.

Bears living along North Pacific beach need to store enough energy before hibernation, Chum Salmons choose to go to risky places in Autumn to spawn, some of them feed bears. Fishman in Amur River area setup net in Autumn, Chum Salmons also feed human. When they are going back from ocean, they are doomed not being able to witness next summer. Even not feeding human and bears, Salmons’ happiest ending also fall prey to the marvellous nature, they will die likely 2 weeks later after they spawn, they use their body to churn the rocks to bury their newly laid eggs in the their last days. No one has explained what they typically died from.

Dead Salmon

桌上足球防守位心得两则

最近公司新来了第二张桌上足球台,球性和第一张完全不同,所以我想某些技巧和心得可能是因球桌而异的。这里记录的是在双打中本人打防守位的一些总结,只针对我司目前破旧生涩的第一张球桌生效。

成功率要比快速出球重要

防守人很怕对方反弹,但是如果反应够快,可以在对方进攻的第一时间 – 对方前锋出脚之后刚刚回收的期间 – 通过类似前锋反弹的击球方式防守,这样可以轻易突破对方锋线把球输送到前场。 – 这就是我之前总结的快速出球打法
对方进攻失败后把球控制住,选择合适的时机合适的角度,用大力射门的方式把球击出。 – 这是成功率打法。

这里说的结论其实是马后炮,因为我见到了成功率打法的拿了我司桌上足球比赛的冠军,而我–快速出球打法的信奉者–表现并不是很好。其实思考原因也很简单, 因为人的力量和反应时间是几乎固定的两个指标,训练到极致也无法突破某个比例,而桌上足球尺寸的大小已经决定了只可能存在完美的进攻,没有完美的防守。所以除非你的前锋比对方前锋把握能力强10倍,否则不要使用快速出球的打法,虽然突破了对方前锋的第一道防线,很大程度上你的前锋也不会能利用好这个机会,所以相比于把球控下来,这样做(快速出球)无异于把控球状态变为开球状态。

防守的选位

防守的两根杆是要跟着当前球所在的位置结合出球点来调整的。当球不在正中路的时候,对方可能的选择路线有:球当前所在边路的三角,直线,撞另一个边路库的大三角。其中最后一种是可能性最小也是留给了我们最长防守时间的,所以正确的站位应该是(下图中o表示球,【】表示球门,|表示你的防守队员)

1
2
3
4
5
6
7
8
9
[ ]
o
。。。。。。
| |
| | |
[ ]

而不是我之前选的

1
2
3
4
5
6
7
8
9
[ ]
o
。。。。。。
| |
| | |
[ ]

因为显然第一种选位对于斜向来球的防守角度更大,且左边后卫离球门更远,减小了撞左后卫脚折射进球门的概率。

A Programmer's Daily Time Distribution And Beyond

As a programmer, I’ve witnessed peers moaning about working-overtime or being pushed by schedule, such as these. Utopia is coding at home with beer aside, pets/kids occasionally interrupt you with their cuteness, but where are your boss and peers in this territory – if you want be a cathedral guy instead of making a living in the bazaar as a vendor, you can’t go through without them. Certainly, working like that won’t maximize your employer’s profits and can’t cooperate with teammates effectively. So that situation is unreachable, we still have to go to office, but at least there’s a way to make yourself really comfortable in office and your employer get the maximum output from you. But how? I happen to have some shower thoughts the other day regarding this.

Consensuses

We need to make some consensus before making a bargain.

First, programmer’s effective input is not measurable, not by working time, not by code-lines. Unlike manufacturing industry, in which qualified parts built by a worker in a unit time is measurable, building software is always a non-linear work, fixing one critical bug may need as much time as writing ten ‘qualified’ features which passed all unit tests and integrational tests, but would fail the stress test, and of course can require as less time as typing several characters if it’s obvious, to someone – I’m not emphasizing this because this example is focus on the diversity of bugs themselves, so programmers’ diversity is not the point.

Second the output is not measurable either, a software is nothing if there’s no user, or user find it hard to use. Even if we don’t consider the money a software can make, or the productivity a software can improve, as metric, just use the software metrics, like story points in the agile context, it is not measurable too. We all experienced two similar stories bidding the same points, but actually the first implemented one values much than the first one, as you know copy&paste constitute most of the most programmer’s activity.

Bearing these in mind, then, from the manager/employer’s perspective, how does he knows his management job is well done, or how is he get the best of his employers? I don’t think there’s any way, person varies with person, if you can not measure their productivity, just believe they are professional(how to ensure this is another topic and is HR’s duty which is answered when he get the offer), and ensure them are productive. If I were a boss, what I would like to is to just make programmers being in a vigorous state, both mental & physical.

Mentally vigorous

It dictates communication in a proper extent. Communicating with others would help you to recognize your issue-to-handle more clearly, but too much of this would blur your focus, make you not-so-targeted – not to mention occupying your time.

Reading an internet post, raising an issue or service request, talking to peers or join a meeting are all kinds of communicating.

It also demand you to distribute your mental activity reasonably. By distribute reasonably, I mean you might need some music or non work chat when you have worked for long time(say longer than 4 four), as long as there’s meal break and coffee break, this would be a problem, the only constraint it brings is not to work over-time heavily and constantly. But it has another meaning which is often ignored, that is even you have 6 hour code time, if it’s broken down into many piecies, I mean divided by meetings, peer-communications, coffee break or internet surfing, it won’t make ‘mental vigorous’ too, with experience, you at least need a block of 1.5 - 2 hours’ time to solve real-challenging problems.

Physical health

I mean cervical/lumbar spondylosis. The 10 tips to prevent lumbar spondylosis or such things always mention don’t keep sitting in 1 hour, walk every 1 hour or so. I’m suggesting this too, actually this didn’t conflict with the 2 hour block you need to solve real-challenge, you can keep thinking of the same issue with this break. And for other breaks outside the 2 hour, talk with peers or go for coffee is surely OK.

Programmer’s daily time distribution

In common sense, to make you productive, yourself or your manager would give you a list of things-to-do, daily or weekly. Books tell you do so too, but as a mental job, things-to-do didn’t always get done even if you assign enough time to it. As I mentioned, inevitable breaks (for mental and physical healthy) and communications didn’t list in your things-to-do, but they actually effect if you can get things done with fixed time. For not-so-competent tasks, you might need more communication. For boring-tasks, you might breaking more, consciously or not. And also for improvement, you need spend time learning, as an employee, you need spend time to meet executive’s requirement, daily task can easily fail if you count in all these. If you log your time by actual items like communication, break, coding, learning&documenting, instead of business items, problems get more clear.

But unfortunately managers often focus the latter, i.e. today you spend 4 hour on issue1, and 4 hour on issue2, why they are not improving? Not until you and your employers start to care about your first log, i.e. daily time distribution(DTD), would the programmer’s life more easier.

What profile does most of the programmer’s DTD look like actually concretize the so called corporational culture. I feel satisfied with my productivity recently, and I think my DTD is reasonable, I’ll give it here:

item time(h)
communication 3
break 1.5
coding 2
learning&documenting 2

If goes into detail, communication includes peer-communication(work and non-work, email or non-email) or searching for internet for solving a problem(like SF), and also for meetings(mostly not-related with your task-to-do today), so actually it not always help you finish your task; break includes coffee break, toilet, table-football, and surfing internet; coding include write code, and miscellaneous tasks like download ide plugin, checking api(in internet or not) but not include things searching SF; learning and documenting include reading-book/posts not directly related with your task in hand, write summary, or log time in JIRA, or write post in Confluence.

It can vary among programmer and production phase, say if not so competent with your current task, you need to learn more, and non-lead programmer can have more time learning. But in general, I say it could profile the corporational culture. Some “performance-targeted” company use story points or features-finished to measure a programmer, this would elongate the code time, and squeezing others, especially learning and break. Some “performance-targeted” company judge programmer with there sounding, thus making unnecessary communication time long. Even not to extent of squeezing physiologic break time, at least it could break the mental vigor. I’m not senior programmer, just 5 years experience with several companies, I never meet any company whose HR/manager would like to survey/query programmer’s DTD, so that they can introspect how they can help programmer to improve productivity. I’m not try to be sensational and union the programmer’s party to do something, but employer does have to discard the one-sided view of software engineering, either just accept it’s a chaos and hence only measure programmer with final result or regard it an analog of manufacturing and hence don’t respect programmer’s job as mental work. It would bring WIN-WIN if employer and programmer start to know DTD and its means.

每个人的五一

有个词叫“伤春悲秋”。所谓悲秋,就是秋凉天里,天朗气清,看见树叶飘零,感到气温下降而唤起一些对大千世界的悲悯,当然也很容易由外而内思及自己。这种体会我是有过的,或者说每年的秋天都有机会体会。然而“伤春”的说法我一直不敢苟同,甚至无法理解,我一直把它当作是被文人硬加进去的无聊的对偶。然而今年,在这个五一,我却有了不一样的体会。

五一她去山西参加闺蜜的婚礼,我会有一个完整的3天!之前一直憧憬的一口气看一整本书,或者在自己的项目上敲一天的代码似乎终于可以实现了。然而把她送到机场回来我就陷到了与孤独苦战的阶段了–原来我面对整块的孤独时间竟然是手足无措的!跟她在手机上诉苦也无济于事,于是我就在看电视,看书,看电脑,看手机之间频繁地切换着。一面给自己压力说不要这样把整块的时间用散了,一面又无法集中精力做一件事情,承认无聊对于我这样自认内在丰富的人来说简直是打脸。

妈妈打电话来了,知道我一个人在家,让我喊陈苏进出去喝酒,不要闷着。我能理解她的心情。这和我看到碗碗懒懒地趴在阳光下就想带它出去散步,或者看到小雪躺在沙发上玩手机就想带她去吃东西看电影一样。然而我告诉她我还要打游戏,告诉她我并不闷。挂完她的电话,我躺在沙发上睡着了。

睡醒之后继续翻书,贪心算法。对于合适的问题,最短视的策略,亦即使每一个当下利益最大化的行动将会得到全局最优结果。好可笑,这让我想起了和郑扬下棋,他从来没有什么固定阵型或者进攻布局,就是想尽一切办法占得局部的便宜–然而我总是输给他–输给了他中轴线上两个马两个炮这样别扭的阵型。我知道有哪里不对,这样走肯定是会有破绽的,但是还没等我找出破绽,我的局地损失已经让我无法翻盘了。这个世界也是这样,你看到人们涌向雄安买房,你不想当中线上两个炮中间的那个马–像个小丑,你觉得哪里不对,这不是兵法上优雅的阵型,然而你却输了。也许活在当下的世界就是那个适合贪心算法的“合适的问题”吧。不学也罢。

我下楼吃了晚饭,带上来可乐和烟,今天的天气真的不错呢。

晚上的球赛并不好看,曼联和阿森纳都踢得很丑,我从来都觉得她影响了我熬夜看球,没想到她不在里屋睡觉会让球赛变得无聊。半夜一点的时候,三儿发了一个朋友圈说五一快乐–配了张出公司的照片–我想表示一下关心,却不想暴露我自己的无聊,只好等明天再说了。是的,不应该这样,明天还是看个电影吧,《记忆大师》好像可以,订个12点的场吧,正好还可以出去吃饭,免得宅到让关心的人感到落寞。

半醒的时候王体虎打来电话,瞎聊了几句,他正在内蒙打算弄个海外食品店,然而内蒙人喝酒的热情却让我的酒桌苦主碰到的麻烦。起床的时候已经11点半了,电影是看不成了,跟三寒暄了几句,让他别太拼了。窗外,风和阳光共同把杨树打造如水晶塔般粼粼可爱,市声远嚣,愈衬安静。朋友们,我祝你们都好,就如同这春光。

Compare Latin Charactors to Basic ASCII Charactor

In some circumstances we meet words that contains Latin charactors, like the word naïve , especially in names like simão. For some reason, we want to translate them to naive, and simao, or at least we can know that they are equal to naive or simao respectively.

I’ve met such a problem recently, and I try to find a solution to this, but honestly, it’s hard to describe such a question. When I browse all the posible related pages which google shows, I find a function in ES6 called normalize which finally helped me out. If you look at the description of the argument of this function, and finally trace to the concept of the so called Canonical Decomposition, you probably would WOW out like me do. Yes, it’s exactly what we want, we want È É Ê Ë being equal to E, want ìíîï all equal to i. Now with this function, we can easily solve the problem with the help of this function, and I’m really glad I found the solution even before I know how to describe the problem.

So here is the utility function

1
2
3
function convertLatin(str) {
return str.normalize("NFD").match(/\w/g).join("");
}

And you’ll find that convertLatin(“naïve”) === “naive”, and convertLatin(“simão”) === “simao”. Enjoy this small utility!

##Update(26 Mar 2017)

After some close investigation, I found the solution above is neither robust nor necessary, as ES6 have provided official support for this user case, please check the new API of
String.prototype.localeCompare
Intl.Collator

十年

—无韵集句 和小智

青山遮不住
毕竟东流去
十年扬州梦
天凉好个秋

总角宴晏晏
岁月忽已晚
幽并游侠儿
萧萧斑马鸣

<转/译>如何将应用配置打包进Docker

粗译

新手开始部署他们的第一个Docker Container的时候经常会问的一个问题就是:”我该怎么把应用的配置打包进Docker容器里面?”.问题中提到的配置包括worker的数量,JVM的内存大小,或者数据库的连接串.现实中实现这些有一套标准方法,而它们各有利弊.

将配置发送到Docker打包了的应用里的三个半方法

1. 将配置烧进容器里

这可能是最简单的配置了,也就是在Dockerfile里面利用COPY指令把配置文件扔到容器里,或者通过RUN指令执行sed以及echo等命令来修改默认的配置文件.

优点:

缺点:

  • 因为配置已经烧到镜像里,未来可能的配置改动都需要修改Dockerfile并重新build来实现

2a. 利用环境变量动态地配置应用

这是一个在Docker Hub上的镜像比较常用的方法,譬如PostgreSQL的’POSTGRES_USER’和’POSTGRES_PASSWORD’这两个环境变量.

简单地说,当你启动容器docker run的时候,需要指定环境变量,而容器的进入点(Entry point)也就是启动脚本会寻找这些变量,并把他们用在相应的配置文件里.

需要提的是,启动脚本应该提供有意义的缺省值,以防用户没有提供这些环境变量.

优点:

  • 从配置角度看,这样的容器更灵活

缺点:

  • 打破了生产/开发环境的一致性要求,也就是说其他人可以通过不同的配置使得容器的行为在生产/开发环境下不一致
  • 一些复杂的配置无法映射为简单的键值对

2b. 利用环境变量动态地配置应用

和上面的一样,但是启动脚本是从网络,像是Consul或者etcd来获取配置参数.

这就使得通过环境变量来实现复杂配置成为可能.因为键值对存储器可以有多层结构.值得一提的是有很多工具可以用来抓取键值对并替换到你的配置文件中.而像confd这类工具甚至可以在配置改变时自动重新加载应用.这就使得应用的配置更加动态化.

优点:

  • 配置更动态
  • 键值存储使得复杂配置成为可能

缺点:

  • 同样违反了生产/开发环境一致性(译注:和所谓的immutable container是同一个概念)
  • KV store必须高可用,因为所有的容器配置都依赖于这个存储器

3. 将配置文件目录挂载到Docker Volumes

Docker Volume介绍略

如果配置文件正好在运行容器的文件系统上,可以通过挂载的方式提供到容器内部使用.例如

docker run -v /home/dan/my_statsd_config.conf:/etc/statsd.conf hopsoft/graphite-statsd

优点:

  • 无需修改容器就可以随意配置

缺点:

  • 违反生产/开发环境一致性要求
  • 如果要用在生产环境中,必须要保证配置文件在基础操作系统中可用.

结论

如上所述,想要配置一个容器包里的应用,方法其实很多,各有利弊.哪个最好?其实取决于你需要多大的动态配置的自由度以及你是否愿意承担额外的譬如维护一个KV store这样的负担.

译后评

个人目前倾向1和2a,但是还没有在生产环境中体验过实际会有哪些坑,所以只能是倾向.

原文地址

一次搭建高性能Nodejs httpServer的尝试(2)

继续上次的.
上次搞的node http server,一个简单的服务器,接收HTTP POST,解析数据入mongo库(nodejs driver用的native driver而非mongoose),主要做了下面的一些优化:

  • 系统层面放开同时打开的文件数(也就是socket数)的限制
  • 复用链接(主要是ab http1.0 keepalive的坑)
  • 增加并发
  • “优化”业务逻辑

其实都是一些”预”优化,在没有需要针对处理的问题出现的情况下先放开一些东西. 后来测试结果满意,一个小项目开始,两周完成了一个小业务之后,需要部署让测试介入.环境一换,问题就来了.

原先在本地的Linux台式机上近16000的TPS到了openstack(4core, 4GB memory)的VM上TPS瞬间掉到了小几千.赶紧登陆上去vmstat查看,发现Procs的r值(等待执行的进程数)接近20,远大于CPU核心数,也就是说CPU成了应用的瓶颈.–原来台式机是8X3.4GHz,到了虚拟机上只有4X2.3GHz,早该想到!

提高虚拟核心数!当然同时也把node.js的slave process提高到8个.同时,把libuv的线程池的限制也放开(设置UV_THREADPOOL_SIZE=8的环境变量),至于这个有没有用,其实我也是不太清楚的,顺便贴一个关于这个问题的争论—好吧,其实是撕逼,吃瓜群众表示看神仙打架也很有意思嘛—也不知道libuv团队最后有没有采纳这个不礼貌的家伙的建议.但是不管libuv的线程池是否应该跟核心数相等,个人觉得不管怎么说,mongodb的native driver开的线程池的大小是5,如果libuv的线程池大小只有4的话肯定不能发挥出其期待的性能吧.再次顺便提一句,mongodb nodejs官方的driver其默认线程池大小也是可以改的–详见参考文档,但是我这里并没有尝试.

好吧,再次测试,TPS又恢复到了16000+. Done!

之后又简单看了一下GC/内存有没有潜在的问题,这也是上一篇文末希望做的.简单来讲做法就是使用node-inspector+Chrome DevTools来比对heap snapshot(和参考文章的工具小有差异)以及使用–trace_gc来查看请求量大量/持久的压力下GC的时间是否能够接受.
但是由于压力较小,没能发现什么—于是就草草地交给测试了.

希望这个DEMO项目能做下去,这样之后说不定在使用中真的就能碰到大数据量的情况,来真正被需求倒逼去进一步探索其他的性能瓶颈—作为一个敏捷开发者(傲娇),我们不提倡提前优化,哈哈.

开发环境的虚拟化

随着Docker越来越火,产品的持续集成,测试,甚至交付(部署)都越来越倾向于使用容器来进行’标准化’.痛苦往往发生在不明白为什么要这么做就被迫跟着走.
但是用着用着确实能感觉到一些方便的地方.我想作为产品开发者,应该是这个Docker化的方案里受益最少的了吧.

最近在关于开发环境如何和Docker集成颇感头疼.最好的结果是开发者能在开发机器上直接使用于测试团队一致的环境进行初步测试/单元测试.对于脚本语言还好–因为开发者需要的其实仅仅是一个文本编辑器而已.但编译语言就不同了,需要编译.如果需要把测试人员的那一套弄到开发者本地,编译这一步到底应该在Docker里面做还是在Docker外面做?拿java来说,IDE一般都支持热部署,其效果就是修改某个java文件后不需要整个替换war包,IDE应该是增量替换了explored的artifact里面的部分class,重新build是很稀少的情况,因此代码-ide-测试是联系在一起的.而如果要测试基于Docker的产品,那么必然需要对每一个改动进行build,对于大的项目,这显然是个灾难.

2017-08-20 更新

去年这个时候的理解还是比较肤浅的,更新一下:

首先澄清初始问题,依据12-factors的要求:Make the tools gap small: keep development and production as similar as possible.
现在看来这里要求的开发和生产环境的一致性其实是在要求CI/CD环境的一致性,或者具体点,是Jenkins Build Node和Production Node的一致性。由于容器技术的引入,其实小环境一致性的要求是自然满足的,而Node系统以及Docker-Engine本身(版本的)一致性,可以很容易地通过复用诸如Chef recipes或者Openstack Heat Template来达到,至于容器编排器的不一致性 – 譬如在Jenkins Slave上用的是docker-compose而在生产环境中使用Kubernetes – 可能造成的问题,我想是Operation需要解决的,毕竟DevOps的存在只是为了让Ops日子好过点,而不是让Ops失去存在的必要。

然后回到开发者视角,具体的问题是:开发者本机上跑的那个开发中的应用/服务应该以容器的形式调试吗?
这是本文最初关注的问题,因为我当时把开发环境理解成了开发者环境,现在看来这个问题已经没有多少意义了,答案是随便。如果是java开发的话,可能你本机的jdk版本跟容器里的jre版本一致比较好,但是其实也无所谓,如果有一些这种环境差异带来的问题,也会以CI的单元测试失败的形式暴露出来。甚至你的开发机器也可以不需要装Docker,因为有Contract Test的保证,你的应用/服务与其他组件集成时可能出现的问题也会在CI过程中以inter-service测试失败的形式暴露出来。当然如果你希望少一点这种类型的返工,还是需要尽量保持开发机器中的单元测试和CI环境下的环境经可能一致 – 在CI里尽可能调用Gradle Task可以很好地帮助我们实现这一点 – 但是这不是必要的,我想说的是12条军规中的关于开发和生产的环境一致性要求是在要求CI和CD的一致性,而非开发者环境和CI环境的一致性,所以作为开发者来说,这个问题可以忽略。