ä»æ¥ã¯ããã®ã·ã¹ãã ã®å¥ã®éšåãã€ãŸããã°ã³ã¬ã¯ã¿ã«ã€ããŠèª¬æãããšãã§ãããã°ã³ã¬ã¯ã¿ã«ã€ããŠã¯ããã®èšäºãšãšãã«ããªãŒãã³ãœãŒã¹ã§æçš¿ããŸãã ã¯ã©ãŠãã®ããžãã¯ã®å€§éšåã¯Goã§èšè¿°ãããŠããããã®ãµãã·ã¹ãã ãäŸå€ã§ã¯ãããŸããã
ã·ã¹ãã ãœãŒã¹ã³ãŒãïŒ github.com/badoo/thunder
ãã®èšäºã§ã¯ãã¯ã©ãŠãã§ã¢ããªã±ãŒã·ã§ã³ãã°ãé ä¿¡ããæ¹æ³ã«ã€ããŠèª¬æããŸãããããåã«ãã¹ã¯ãªãããã¬ãŒã ã¯ãŒã¯ããšåŒã³ãŸãã
ã¢ããªã±ãŒã·ã§ã³ãã°
ã¯ã©ãŠãã§å®è¡ãããã¢ããªã±ãŒã·ã§ã³ã¯PHPã¯ã©ã¹ã§ãããæãåçŽãªå®è£ ã§ã¯runïŒïŒã¡ãœãããæã¡ãããšãã°1ãNã®æ°ã®ãžã§ãããŒã¿ãåãåããŸããNã¯ãã®ã¯ã©ã¹ã®ã€ã³ã¹ã¿ã³ã¹ã®æ倧æ°ã§ãã åã¿ã¹ã¯ã«ã¯åºæã®IDããããæçµçãªç®æšã¯ãç¹å®ã®èµ·åã®ãã°ãšã¯ã©ã¹ã®ãã¹ãŠã®ãã°ãäžåºŠã«ç°¡åã«èŠã€ããããšãã§ããéäžãªããžããªã«ãã°ãé ä¿¡ããããšã§ãã
<?php class ExampleScript extends ScriptSimple { public function run() { $this->getLogger()->info("Hello, world!"); return true; } }
æåã®å®è£ ïŒèµ·åIDã®ãã¡ã€ã«ããš
ã¯ã©ãŠãå ã®ã¿ã¹ã¯ã®åèµ·åã¯åå¥ã®PHPããã»ã¹ã®èµ·åãè¡šããŠãããããåèµ·åã®ãã°ãåå¥ã«åéããæãç°¡åã§æçœãªæ¹æ³ã¯ãåããã»ã¹ã®åºåã<id>ã<Out | err> .logã®åœ¢åŒã®åå¥ã®ãã¡ã€ã«ã«ãªãã€ã¬ã¯ãããããšã§ããoutããã³errã¯ãããããæšæºåºåãã£ãã«ãšãšã©ãŒã«äœ¿çšãããŸãã
ãã®ããããã°ã³ã¬ã¯ã¿ãŒã®ã¿ã¹ã¯ã¯ãå®æçã«ãã£ã¬ã¯ããªã«å€æŽã®ãã°ãç §äŒãããã¡ã€ã«ã«çŸããæ°ããè¡ãéä¿¡ããããšã§ããã ãã°ãäžå€®ãµãŒããŒã«é ä¿¡ããæ段ãšããŠã¹ã¯ã©ã€ãã䜿çšããæåŸã«éä¿¡ããããªãã»ããããã¡ã€ã«åã«çŽæ¥ä¿åããŸããïŒããã¯ãéããŠãããã¡ã€ã«èšè¿°åã«ãã°ãæžãç¶ããå Žåã«æ©èœããŸãïŒã ãªãã»ããã¯éä¿¡æã®ãã¡ã€ã«ãµã€ãºã§ããæ°ãããã°ããã¡ã€ã«ã«æžã蟌ãŸãããšãµã€ãºã倧ãããªãããã¡ã€ã«å ã®æåŸã«é ä¿¡ãããäœçœ®ããæ°ããè¡ãé ä¿¡ããå¿ èŠããããŸãã
<?php // while (true) { foreach (glob("*.log") as $filename) { $filesize = filesize($filename); // 200 $read_offset = parseOffset($filename); // "id.out.log.100" -> 100 if ($filesize > $read_offset) { sendToScribe($filename, $read_offset); // scribe $read_offset rename($filename, replaceOffset($filename, $filesize); // "id.out.log.100" -> "id.out.log.200" } else if (finishedExecution($filename)) { unlink($filename); } } sleep(1); }
ãã£ã¬ã¯ããªå ã«å°æ°ã®ãã¡ã€ã«ãããããããããå€ããå°ãªãã掻çºã«æžã蟌ã¿ãè¡ã£ãŠããéãããã®ã¢ãããŒãã¯ããŸãæ©èœããŸãã ã¢ããªã±ãŒã·ã§ã³ãè¡ã®å é ã«èµ·åèå¥åãè¿œå ããããã¬ãŒãã䜿çšãã代ããã«åçŽãªãšã³ãŒãäœæããå Žåã§ããåå¥ã®ãã¡ã€ã«ãžã®ãªãã€ã¬ã¯ãã«ãããåèµ·åã®åºåãåå¥ã«ç°¡åã«åºå¥ã§ããŸãã åããã¡ã€ã«ãžã®æžã蟌ã¿ãšæ¯èŒãããšããã®å Žåãã¢ããªã±ãŒã·ã§ã³ã®ç°ãªããã€ã³ã¹ã¿ã³ã¹ãããã®åºåãæ··åšãããããšã¯ã§ããŸããã ãŸããä»ã®èª°ããã¡ã€ã«ã«æžã蟌ãŸãªãããšãç解ããã®ã¯ç°¡åã§ããæå®ãããIDã®ããã»ã¹ãæ¢ã«å®äºããŠããå Žåãã¹ã¯ã©ã€ãã«å®å šã«é ä¿¡ããããšãã«å¯Ÿå¿ãããã°ãã¡ã€ã«ãåé€ã§ããŸãã
ãã ãããã®æ¹åŒã«ã¯å€ãã®æ¬ ç¹ããããŸãã äž»ãªãã®ã¯æ¬¡ã®ãšããã§ãã
- ãã¡ã€ã«åã«ã¯ã¯ã©ã¹åã«é¢ããæ å ±ãå«ãŸããŠããŸãã-ãã®æ å ±ã¯ã¯ã©ãŠãããŒã¹ããèŠæ±ããå¿ èŠããããŸãã
- ã¹ã¯ã©ã€ãã§ã¯ãå®å ãµãŒããŒãåŠçãããããã¯ããã«å€ãã®ããŒã¿ãç°¡åã«ã移åãã§ããŸãã ãã®ç¶æ³ã§ã¯ãã¹ã¯ã©ã€ãã¯ããŒã¿ããã¡ã€ã«ã·ã¹ãã ã«ããŒã«ã«ã«ãããã¡ãªã³ã°ãããã§ã«ãã£ã¹ã¯ã«ãããã°ãè€è£œããŸãã
- ãã°ã³ã¬ã¯ã¿ãŒãå€ããã¡ã€ã«ãåé€ããæéããªããªããšãå€ãã®ãã¡ã€ã«ãèç©ãããå¯èœæ§ããããŸãã ãã¹ãããšã«æ°çŸäžã®ãã¡ã€ã«ãæ°åèç©ããŸããããå¿ èŠãªãã°ããŸã é¢é£ãããŸã§ã«é ä¿¡ããæ¹æ³ããããŸããã§ããã
- å€ãã®ãã¡ã€ã«ã絶ããäœæãååå€æŽãåé€ãããšãext3ãã¡ã€ã«ã·ã¹ãã ïŒããã³ext4çšåºŠïŒã®åäœãããŸããããããŸããããã¡ã€ã«ãžã®æžã蟌ã¿æããã³äœææã«ãDç¶æ ã§ããã»ã¹ãæ°çŸããªç§ãã¹ã¿ãã¯ãããããšããããããŸãã ;
- statïŒïŒãã¡ã€ã«ã®çµ¶ãéãªãããŒãªã³ã°ãåãé€ããinotifyã®äœ¿çšãéå§ãããå Žåã¯ãäžå¿«ãªé©ãããããŸãã 倧éã®ç©ºãã¡ã¢ãªããããã«ãã³ã¢ã·ã¹ãã ã§ç¹ã«é¡èãªå®è£ æ©èœã«ããããã¡ã€ã«ãå®æçã«äœæããã³åé€ããããã£ã¬ã¯ããªã§inotify_add_watchïŒïŒãåŒã³åºããããšããã®ãã£ã¬ã¯ããªå ã®ãã¡ã€ã«ã«æžã蟌ããã¹ãŠã®ããã»ã¹ã®ãåºçããçºçããå ŽåããããŸãããããŠããã¯æ°åç§éç¶ãããšãã§ããŸãã
ãã©ã°ã©ãïŒ5ïŒã§èª¬æãããŠããæ¡ä»¶äžã§ã®ãäžæ£ãªãinotifyåäœã®åå ã«ã€ããŠè©³ããç¥ãããå Žåã¯ã以äžã®ãã¿ãã¬ãèªãã§ãã ããã
éåžžã«é
ãinotify_add_watchïŒïŒã®çç±
ãã©ã°ã©ãïŒ5ïŒã§èª¬æããããã«ããã°ã®ãããã£ã¬ã¯ããªããããŸããã ãã®ãã£ã¬ã¯ããªã§ã¯ãå€æ°ã®ãã¡ã€ã«ã絶ããäœæãåé€ãããã³ååå€æŽãããŸããã ãã¡ã€ã«ã«ã¯èµ·åIDãšèªã¿åããªãã»ãããå«ãŸããŠããããããã¡ã€ã«ã«ã¯äžæã®ååãå«ããããšãéèŠã§ãã
ãã®åé¡ã¯ãå°èŠæš¡ã§ã¯ãããŸãããã¡ã¢ãªãå°ãªãã·ã³ã°ã«ã³ã¢ã·ã¹ãã ã§ãç°¡åã«åçŸã§ããŸãã ãã®èšäºã«èšèŒãããŠããæ°å€ã¯ãæ°åã®ã¬ãã€ãã®ã¡ã¢ãªãæèŒãããã«ãã³ã¢ãã·ã³ã§åŸããããã®ã§ãã
空ã®ãã£ã¬ã¯ããªãäœæããtmpãªã©ã®ååãä»ããŸãã ãã®åŸãç°¡åãªã¹ã¯ãªãããå®è¡ããŸãã
ãã®ã¹ã¯ãªãããè¡ãããšã¯ãfileNãšãã圢åŒã®ååšããªããã¡ã€ã«ã«å¯ŸããŠstatïŒïŒãŸãã¯accessïŒïŒã1000äžåå®è¡ããããšã§ãïŒNã¯0ã9,999,999ã®æ°åã§ãïŒã
次ã«ãinotify_add_watchã·ã¹ãã ã³ãŒã«ãè¡ããŸãïŒinotifyã䜿çšããŠãã£ã¬ã¯ããªãžã®å€æŽã®ç£èŠãéå§ããŸãïŒã
straceã®-TTãã©ã°ã«ããââãã·ã¹ãã ã³ãŒã«ã¯è¡æ«ã§æ°ç§ã§å®è¡ãããŸãã æ°ããã€ãã³ãã®éç¥çšã®ãªã¹ãã«ç©ºã®ãã£ã¬ã¯ããªã1ã€è¿œå ããã·ã¹ãã ã³ãŒã«ã«ã¯ãæ°çŸããªç§ã®æéãããããŸããã ãã®ãããªåçŽãªå®éšã®æ çµã¿ã§ã¯ãæ¬çªã·ã¹ãã ã§èŠ³å¯ããæ°åç§ãååŸããããšã¯å°é£ã§ãããåé¡ã¯äŸç¶ãšããŠååšããŸãã æ°ãã空ã®tmp2ãã£ã¬ã¯ããªãäœæããŠããã¹ãŠãããã«æ©èœããããšã確èªããŸãããã
æ°ããäœæããã空ã®ãã£ã¬ã¯ããªã§ã¯ãé¡äŒŒãããã®ã¯äœã芳å¯ãããªãããšãããããŸããã·ã¹ãã ã³ãŒã«ã¯ã»ãŒç¬æã«åŠçãããŸãã
ååšããªããã¡ã€ã«ããstatïŒïŒãäœåºŠãå®è¡ããããã£ã¬ã¯ããªã«åé¡ãããçç±ãèŠã€ããããã«ãçµäºããªãããã«ãœãŒã¹ããã°ã©ã ãå°ãå€æŽããŠããã®ããã»ã¹ã®perf topã³ãã³ãã®çµæã確èªããŸãã
ã»ãŒ100ïŒ ã®æéãã«ãŒãã«å ã®1åã®åŒã³åºãïŒ__fsnotify_update_child_dentry_flagsïŒã«è²»ããããŠããããšãããããŸãã Linuxã«ãŒãã«ããŒãžã§ã³3.16ã§èŠ³å¯ãè¡ãããŸããããä»ã®ããŒãžã§ã³ã§ã¯çµæãè¥å¹²ç°ãªãå ŽåããããŸãã ãã®é¢æ°ã®ãœãŒã¹ã³ãŒãã¯ã次ã®ã¢ãã¬ã¹ã§è¡šç€ºã§ããŸãïŒ git.kernel.org/cgit/linux/kernel/git/torvalds/linux.git/tree/fs/notify/fsnotify.c?id=v3.16
ãããã°printkãè¿œå ããããperfã®çµæãèŠããšã次ã®å Žæã§åé¡ãçºçããããšãååã«ç¢ºèªã§ããŸãã
æå®ããããã£ã¬ã¯ããªå ã®ãã¡ã€ã«ã®å€æŽã®ç£èŠãéå§ããããã«ãã«ãŒãã«ã¯ã倧ãŸãã«èšããšãfilenameã=> inode dataã®åœ¢åŒã®ãã£ãã·ã¥ãå«ãdentryæ§é ãééããŸãã ãã®ãã£ãã·ã¥ã¯ãèŠæ±ããããã¡ã€ã«ãååšããªãå Žåã§ãèªã¿èŸŒãŸããŸãïŒ ãã®å Žåãd_inodeãã£ãŒã«ãã¯ãŒãã«ãªããæ¡ä»¶ã§ãã§ãã¯ãããŸãã ãããã£ãŠãinotify_add_watchãåŒã³åºããããšãã«ãŒãã«ã¯æå®ããããã£ã¬ã¯ããªã®ïŒãã®å Žåã¯å·šå€§ãªïŒdentryãã£ãã·ã¥ãééãããã£ã¬ã¯ããªãå®éã«ç©ºã§ããããããã¹ãŠã®èŠçŽ ãã¹ãããããŸãã ãã®ãã£ãã·ã¥ã®ãµã€ãºãšãããã¯ã®ç«¶åãã«å¿ããŠããã®ãã£ã¬ã¯ããªãšå éšã«å«ãŸãããã¡ã€ã«ãæäœããæ©èœããããã¯ããªãããã·ã¹ãã ã³ãŒã«ã«éåžžã«é·ãæéããããå ŽåããããŸãã
æ®å¿µãªããããã®åé¡ã¯ç°¡åã«è§£æ±ºã§ãããVFSã¬ã€ã€ãŒãšdentryãµãã·ã¹ãã ã®ã¢ãŒããã¯ãã£äžã®åé¡ã§ãã æçœã§ç°¡åãªè§£æ±ºçã®1ã€ã¯ãååšããªããšã³ããªã®æ倧ãã£ãã·ã¥ãµã€ãºã«å¶éã課ãããšã§ãããããã«ã¯VFSã¢ãŒããã¯ãã£ã®é倧ãªå€æŽãšãçŸåšã®åäœã«äŸåããå€æ°ã®æ©èœã®æžãæããå¿ èŠã§ãã ååšããªããã¡ã€ã«ã®ãã£ãã·ã¥ã®ã«ãŠã³ã¿ãŒãååšãããšãVFSãµãã·ã¹ãã å šäœã®ããã©ãŒãã³ã¹ãäœäžããå¯èœæ§ããããŸãã ãã®åé¡ã®åå ãçªãæ¢ãããšãããããä¿®æ£ããããšããã«ãåé¿ããããšã«ããŸããïŒinotifyã§ç£èŠãããã£ã¬ã¯ããªã«äžæã®ååãæã€ãã¡ã€ã«ãäœæããªããªãããã®ããdentryãã£ãã·ã¥ãè©°ãŸãããŸããã ãã®æ¹æ³ã¯åé¡ãå®å šã«è§£æ±ºããé倧ãªäžäŸ¿ãçããããŸããã
ãã®åé¡ã¯ãå°èŠæš¡ã§ã¯ãããŸãããã¡ã¢ãªãå°ãªãã·ã³ã°ã«ã³ã¢ã·ã¹ãã ã§ãç°¡åã«åçŸã§ããŸãã ãã®èšäºã«èšèŒãããŠããæ°å€ã¯ãæ°åã®ã¬ãã€ãã®ã¡ã¢ãªãæèŒãããã«ãã³ã¢ãã·ã³ã§åŸããããã®ã§ãã
空ã®ãã£ã¬ã¯ããªãäœæããtmpãªã©ã®ååãä»ããŸãã ãã®åŸãç°¡åãªã¹ã¯ãªãããå®è¡ããŸãã
$ mkdir tmp $ cat flood.php <?php for ($i = 0; $i < $argv[1]; $i++) { file_exists("tmp/file$i"); } $ php flood.php 10000000
ãã®ã¹ã¯ãªãããè¡ãããšã¯ãfileNãšãã圢åŒã®ååšããªããã¡ã€ã«ã«å¯ŸããŠstatïŒïŒãŸãã¯accessïŒïŒã1000äžåå®è¡ããããšã§ãïŒNã¯0ã9,999,999ã®æ°åã§ãïŒã
次ã«ãinotify_add_watchã·ã¹ãã ã³ãŒã«ãè¡ããŸãïŒinotifyã䜿çšããŠãã£ã¬ã¯ããªãžã®å€æŽã®ç£èŠãéå§ããŸãïŒã
$ cat inotify_test.c #include <sys/inotify.h> void main(int argc, char *argv[]) { inotify_add_watch(inotify_init(), argv[1], IN_ALL_EVENTS); } $ gcc -o inotify_test inotify_test.c $ strace -TT -e inotify_add_watch ./inotify_test tmp inotify_add_watch(3, "tmp", âŠ) = 1 <0.364838>
straceã®-TTãã©ã°ã«ããââãã·ã¹ãã ã³ãŒã«ã¯è¡æ«ã§æ°ç§ã§å®è¡ãããŸãã æ°ããã€ãã³ãã®éç¥çšã®ãªã¹ãã«ç©ºã®ãã£ã¬ã¯ããªã1ã€è¿œå ããã·ã¹ãã ã³ãŒã«ã«ã¯ãæ°çŸããªç§ã®æéãããããŸããã ãã®ãããªåçŽãªå®éšã®æ çµã¿ã§ã¯ãæ¬çªã·ã¹ãã ã§èŠ³å¯ããæ°åç§ãååŸããããšã¯å°é£ã§ãããåé¡ã¯äŸç¶ãšããŠååšããŸãã æ°ãã空ã®tmp2ãã£ã¬ã¯ããªãäœæããŠããã¹ãŠãããã«æ©èœããããšã確èªããŸãããã
$ mkdir tmp2 $ strace -TT -e inotify_add_watch ./inotify_test tmp2 inotify_add_watch(3, "tmp2", âŠ) = 1 <0.000014>
æ°ããäœæããã空ã®ãã£ã¬ã¯ããªã§ã¯ãé¡äŒŒãããã®ã¯äœã芳å¯ãããªãããšãããããŸããã·ã¹ãã ã³ãŒã«ã¯ã»ãŒç¬æã«åŠçãããŸãã
ååšããªããã¡ã€ã«ããstatïŒïŒãäœåºŠãå®è¡ããããã£ã¬ã¯ããªã«åé¡ãããçç±ãèŠã€ããããã«ãçµäºããªãããã«ãœãŒã¹ããã°ã©ã ãå°ãå€æŽããŠããã®ããã»ã¹ã®perf topã³ãã³ãã®çµæã確èªããŸãã
$ cat inotify_stress_test.c #include <sys/inotify.h> void main(int argc, char *argv[]) { int ifd = inotify_init(); int wd; for (;;) { wd = inotify_add_watch(ifd, argv[1], IN_ALL_EVENTS); inotify_rm_watch(ifd, wd); } } $ gcc -o inotify_stress_test inotify_stress_test.c $ strace -TT -e inotify_add_watch,inotify_rm_watch ./inotify_stress_test tmp inotify_add_watch(3, "tmp", âŠ) = 1 <0.490447> inotify_rm_watch(3, 1) = 0 <0.000204> inotify_add_watch(3, "tmp", âŠ) = 2 <0.547774> inotify_rm_watch(3, 2) = 0 <0.000015> inotify_add_watch(3, "tmp", âŠ) = 3 <0.466199> inotify_rm_watch(3, 3) = 0 <0.000016> ⊠$ sudo perf top -p <pid> 99.71% [kernel] [k] __fsnotify_update_child_dentry_flags âŠ
ã»ãŒ100ïŒ ã®æéãã«ãŒãã«å ã®1åã®åŒã³åºãïŒ__fsnotify_update_child_dentry_flagsïŒã«è²»ããããŠããããšãããããŸãã Linuxã«ãŒãã«ããŒãžã§ã³3.16ã§èŠ³å¯ãè¡ãããŸããããä»ã®ããŒãžã§ã³ã§ã¯çµæãè¥å¹²ç°ãªãå ŽåããããŸãã ãã®é¢æ°ã®ãœãŒã¹ã³ãŒãã¯ã次ã®ã¢ãã¬ã¹ã§è¡šç€ºã§ããŸãïŒ git.kernel.org/cgit/linux/kernel/git/torvalds/linux.git/tree/fs/notify/fsnotify.c?id=v3.16
ãããã°printkãè¿œå ããããperfã®çµæãèŠããšã次ã®å Žæã§åé¡ãçºçããããšãååã«ç¢ºèªã§ããŸãã
/* run all of the children of the original inode and fix their * d_flags to indicate parental interest (their parent is the * original inode) */ spin_lock(&alias->d_lock); list_for_each_entry(child, &alias->d_subdirs, d_u.d_child) { if (!child->d_inode) continue;
æå®ããããã£ã¬ã¯ããªå ã®ãã¡ã€ã«ã®å€æŽã®ç£èŠãéå§ããããã«ãã«ãŒãã«ã¯ã倧ãŸãã«èšããšãfilenameã=> inode dataã®åœ¢åŒã®ãã£ãã·ã¥ãå«ãdentryæ§é ãééããŸãã ãã®ãã£ãã·ã¥ã¯ãèŠæ±ããããã¡ã€ã«ãååšããªãå Žåã§ãèªã¿èŸŒãŸããŸãïŒ ãã®å Žåãd_inodeãã£ãŒã«ãã¯ãŒãã«ãªããæ¡ä»¶ã§ãã§ãã¯ãããŸãã ãããã£ãŠãinotify_add_watchãåŒã³åºããããšãã«ãŒãã«ã¯æå®ããããã£ã¬ã¯ããªã®ïŒãã®å Žåã¯å·šå€§ãªïŒdentryãã£ãã·ã¥ãééãããã£ã¬ã¯ããªãå®éã«ç©ºã§ããããããã¹ãŠã®èŠçŽ ãã¹ãããããŸãã ãã®ãã£ãã·ã¥ã®ãµã€ãºãšãããã¯ã®ç«¶åãã«å¿ããŠããã®ãã£ã¬ã¯ããªãšå éšã«å«ãŸãããã¡ã€ã«ãæäœããæ©èœããããã¯ããªãããã·ã¹ãã ã³ãŒã«ã«éåžžã«é·ãæéããããå ŽåããããŸãã
æ®å¿µãªããããã®åé¡ã¯ç°¡åã«è§£æ±ºã§ãããVFSã¬ã€ã€ãŒãšdentryãµãã·ã¹ãã ã®ã¢ãŒããã¯ãã£äžã®åé¡ã§ãã æçœã§ç°¡åãªè§£æ±ºçã®1ã€ã¯ãååšããªããšã³ããªã®æ倧ãã£ãã·ã¥ãµã€ãºã«å¶éã課ãããšã§ãããããã«ã¯VFSã¢ãŒããã¯ãã£ã®é倧ãªå€æŽãšãçŸåšã®åäœã«äŸåããå€æ°ã®æ©èœã®æžãæããå¿ èŠã§ãã ååšããªããã¡ã€ã«ã®ãã£ãã·ã¥ã®ã«ãŠã³ã¿ãŒãååšãããšãVFSãµãã·ã¹ãã å šäœã®ããã©ãŒãã³ã¹ãäœäžããå¯èœæ§ããããŸãã ãã®åé¡ã®åå ãçªãæ¢ãããšãããããä¿®æ£ããããšããã«ãåé¿ããããšã«ããŸããïŒinotifyã§ç£èŠãããã£ã¬ã¯ããªã«äžæã®ååãæã€ãã¡ã€ã«ãäœæããªããªãããã®ããdentryãã£ãã·ã¥ãè©°ãŸãããŸããã ãã®æ¹æ³ã¯åé¡ãå®å šã«è§£æ±ºããé倧ãªäžäŸ¿ãçããããŸããã
ã¯ã©ã¹åããã¡ã€ã«ã«è¿œå ããããšã§ãã¯ã©ãŠãããŒã¹ã«ãªã¯ãšã¹ããè¡ãå¿ èŠããããšããåé¡ã解決ã§ããŸããããã以å€ã¯ããã»ã©ãã©è²ã§ã¯ãããŸããã ãŠãŒã¶ãŒã«ãã¬ãŒã®äœ¿çšã匷å¶ããã«ãåãã¢ããªã±ãŒã·ã§ã³ã®ç°ãªãã€ã³ã¹ã¿ã³ã¹ããåºåãåé¢ããæ©èœãç¶æããããã«ãã¢ããªã±ãŒã·ã§ã³ã®åºåããã¡ã€ã«ã§ã¯ãªããUnixãã€ããã«ãªãã€ã¬ã¯ãããããšã¯å¯èœã§ãããããã¯æ°ããåé¡ãäœæããŸã-æŽæ°ããå¿ èŠãããå Žåãããã·ã³ãŒãïŒPHPã¯ã©ã¹ãå®è¡ïŒããå£ãããã€ããïŒå£ãããã€ãïŒã«æžã蟌ãããšãããšãçŸåšã®ã¿ã¹ã¯ã®äœæ¥ãäžæãããå ŽåããããŸãã
ããã¯ãããŒã¢ã³ãåèµ·åããããšããã€ãã®èªã¿åãåŽã«å¯Ÿå¿ãããã¹ãŠã®èšè¿°åãéããããåŸã§æžã蟌ã¿ãè©Šã¿ããšãããã»ã¹ãSIGPIPEãåä¿¡ããŠââçµäºããããã§ãã ã¡ãªã¿ã«ãheadãŠãŒãã£ãªãã£ãŒãªã©ã䜿çšããunixã³ãã³ãã®ãã§ãŒã³ã®æäœã¯ããã®ã¡ã«ããºã ã«åºã¥ããŠããŸããã³ãã³ãcat some_file.txt | å¿ èŠãªè¡æ°ãèªã¿åã£ãåŸãheadã³ãã³ãã¯åçŽã«çµäºãã察å¿ãããã€ããäžæããæåŸãŸã§æžã蟌ã¿ãç¶ããcatããã»ã¹ãSIGPIPEã·ã°ãã«ãåä¿¡ããå®è¡ãåã«çµäºãããããheadã¯ãšã©ãŒã¡ãã»ãŒãžã衚瀺ããŸããã ãã§ãŒã³ã«è€æ°ã®ããã»ã¹ãããå Žåããã§ãŒã³ã®åèŠçŽ ã§åãç¶æ³ãçºçãããã¹ãŠã®äžéã¢ããªã±ãŒã·ã§ã³ã¯SIGPIPEã·ã°ãã«ã§æ£åžžã«çµäºããŸãã
ãéåžžã®ãUNIXãã€ãããååä»ããååä»ããã€ãã«çœ®ãæããããšãã§ããŸããã€ãŸãããã¡ã€ã«ãžã®æžã蟌ã¿ãç¶ããŸããååä»ããã€ãã¯ç°ãªãã¿ã€ãã®ã¿ã§ãã ãã ããã¯ã©ãã·ã¥ãç°¡åã«ä¹ãè¶ããŠãããã·ãåèµ·åã§ããããã«ããã«ã¯ããã¡ã€ã«åãšèµ·åIDã®å¯Ÿå¿ã«é¢ããæ å ±ãã©ããã«çœ®ãå¿ èŠããããŸãã ãã®ãããªãªãã·ã§ã³ã®1ã€ã¯ãã¡ã€ã«åèªäœã§ãå ã®åé¡ã«æ»ããŸãã ä»ã®ãªãã·ã§ã³ã¯ããããå¥ã®ããŒã¿ããŒã¹ãããšãã°sqliteãrocksdbã«ä¿åããããšã§ãããããã¯ãã®ãããªäžèŠåââçŽãªã¿ã¹ã¯ã«ã¯æ±ãã«ãããšæãããåæã«2ãã§ãŒãºã³ãããã®åé¡ãè¿œå ããŸãïŒæ°ããéå§IDããã€ãã«å ±åããããšãïŒãŸãããã®æç¹ã§èªã¿åãããã»ã¹ãçµäºãããããããŒã¿ããŒã¹å ã®ã¬ã³ãŒãã¯æŽæ°ããããèªã¿åãããã»ã¹ã®æ¬¡ã®ã€ã³ã«ããŒã·ã§ã³ã§ã¯ãèµ·åIDããŸã å€ããšæ³å®ãããŸãïŒã
解決ç
æ°ãããœãªã¥ãŒã·ã§ã³ã«ã¯ã©ã®ãããªæ©èœãå¿ èŠã§ããïŒ
- ã³ã³ããŒãã³ãïŒãããã·ããã°ã³ã¬ã¯ã¿ãŒãããã³å®å ãµãŒããŒïŒã®åèµ·åãšã¯ã©ãã·ã¥ã«å¯Ÿããæµæã
- ã¯ã©ã¹ã®1ã€ãåŠçããæéããªãã»ã©å€ãã®ãã°ãæžã蟌ãå Žåãä»ã®ã¯ã©ã¹ã®ãã°ã¯èš±å®¹å¯èœãªæéå ã«é ä¿¡ãããéçºè ã衚瀺ã§ããããã«ããå¿ èŠããããŸãã
- ãã°é ä¿¡ã®åé¡ã«ã€ããŠã¯ãç¶æ³ãå¶åŸ¡äžèœã«ãªãããšã¯ãªããæåã§ç°¡åã«ä¿®æ£ã§ããå¿ èŠããããŸãïŒããšãã°ãæ°çŸäžã®ãã¡ã€ã«ãäœæããªãã§ãã ããïŒã
- å¯èœã§ããã°ãã·ã¹ãã ã¯ãªã¢ã«ã¿ã€ã ã§ããã垯åå¹ ã倧éã«äŸçµŠãããŠããå¿ èŠããããŸãã
äžèšã®inotifyããã³dentryãã£ãã·ã¥ã®ç®è©°ãŸãã®åé¡ã«ãããæ°ããåè·¯ã¯åžžã«åãååã®ãã¡ã€ã«ã«æžã蟌ãå¿ èŠããããŸãã åçŽã§è«ççãªãœãªã¥ãŒã·ã§ã³ãšããŠãã¢ããªã±ãŒã·ã§ã³ã®åºåãclass_name.out.logã®åœ¢åŒã®ãã¡ã€ã«ã«æžã蟌ã¿ãå®æçã«ããŒããŒã·ã§ã³ããŠãããšãã°class_name.out.log.oldãåŒã³åºããŸãã æ®å¿µãªãããç°ãªãã€ã³ã¹ã¿ã³ã¹ã®ãã°ãåããã¡ã€ã«ã«æžã蟌ãã«ã¯ã¢ããªã±ãŒã·ã§ã³ã®å€æŽãå¿ èŠã§ãïŒä»¥åã«åçŽãªãšã³ãŒãå®è¡ããããšãèš±ãããŠããå Žåãæ°ããã¹ããŒã ã§ã¯ãåè¡ã«èµ·åèå¥åãæã€ã¿ã°ãè¿œå ãããã¬ãŒãåžžã«äœ¿çšããå¿ èŠããããŸãã åæã«èšé²ããªããflockïŒïŒã䜿çšããããšãããã©ãŒãã³ã¹ãå€§å¹ ã«äœäžããã1ã€ã®ãã¹ã¿ãã¯ããã»ã¹ããçŸåšã®ãµãŒããŒã§ãã®ã¢ããªã±ãŒã·ã§ã³ã®ä»ã®ãã¹ãŠã®ã€ã³ã¹ã¿ã³ã¹ã®å®è¡ããããã¯ããå¯èœæ§ããããããæãŸãããããŸããã flockïŒïŒã䜿çšãã代ããã«ããã¡ã€ã«ãO_APPENDã¢ãŒãïŒãã©ã°aïŒã§éããåã¬ã³ãŒããã¢ãããã¯ã«ãªãããã«4 KB以äžïŒLinuxã®å ŽåïŒã®ãããã¯ã§æžã蟌ãããšãã§ããŸãã
ãããã£ãŠãããã¡ã€ã«ããå®è¡ãã§ã¯ãªãããã¡ã€ã«ããã¯ã©ã¹ãã«æžã蟌ãã ãã§ããã€ã³ã1ãš3ã解決ããŸããã
ãã°ãåéããæ¹æ³ã¯ïŒ
ãã®ãããinotifyãå€æ°ã®ãã¡ã€ã«ããããã·ã¯ã©ãã·ã¥ãžã®æµæã«é¢ããåé¡ã®è§£æ±ºçãèŠã€ããŸããã ãããã®ãã°ãåéããæ¹æ³ãç解ããããšã¯ä»ã§ãæ®ã£ãŠããŸãã è«ççãªè§£æ±ºçã¯ãåã«syslogãæ®ãããsyslog-ngãªã©ã®é¡äŒŒç©ã䜿çšããããšã§ãã ãã ããå®éã«ã¯æ¢ã«ãã°ããã¡ã€ã«ã«æžã蟌ãã§ããã®ã§ã代ããã«ãããã®ãã¡ã€ã«ã®å 容ã®åçŽãªãã¹ããªãŒã ããäžå€®ãµãŒããŒã«æžã蟌ãããšãã§ããŸãã ãã€ã¢ã°ã©ã ã¯æ¬¡ã®ããã«ãªããŸãã
å³ãããããããã«ã2ã€ã®å€§ããªãµãã·ã¹ãã ããããŸãããµãŒããŒã¬ã·ãŒããŒïŒããã»ããµïŒãšåãã·ã³ã®ãã°ã³ã¬ã¯ã¿ãŒïŒã³ã¬ã¯ã¿ãŒïŒã§ãã
ã¬ã·ãŒããŒãšã³ã¬ã¯ã¿ãŒéã®éä¿¡ã¯ãåžžã«ç¢ºç«ãããTCP / IPæ¥ç¶ã䜿çšããŠå®è¡ãããGoogleãããã³ã«ãããã¡ãŒã¯ãã±ããã®ããã±ãŒãžåã«äœ¿çšãããŸãã inotifyã䜿çšããã³ã¬ã¯ã¿ãŒã¯ããã¡ã€ã«ã®å€æŽã远跡ããæ°ããè¡ã®ãã±ãããåä¿¡è ã«éä¿¡ããŸãã 次ã«ããœãŒã¹ãµãŒããŒäžã®ãã¡ã€ã«ã§åä¿¡ããïŒããã³ãã°ãã¡ã€ã«ã«æ£åžžã«æžã蟌ãŸããïŒãªãã»ãããéãè¿ããŸãã
ã¬ã·ãŒããŒã¯ãå®æçã«ïŒãã®å®è£ ã§ã¯1ç§éã«1åïŒãªã¹ã[{InodeïŒ...ãOffsetïŒ...}ã...]ã®åœ¢åŒã§æ°ãããªãã»ãããåå¥ã®JSONãã¡ã€ã«ã«ãªã»ããããŸãã ãã®ã¹ããŒã ã«ããããããã¯ãŒã¯é害ã«èããããšãã§ããŸããããµãŒããŒã®é»æºé害ãã«ãŒãã«ãããã¯ããä¿è·ããããšã¯ã§ããŸããã ãã®åé¡ã¯ç§ãã¡ã«ãšã£ãŠéèŠã§ã¯ãªããããã¬ã·ãŒããŒã¯ãå®éã®ããŒã¿ããã£ã¹ã¯ã«ãã©ãã·ã¥ãããã®ãåŸ ããã«ãwriteïŒïŒã®åŒã³åºããæåããåŸãèšé²ãããããŒã¿ã«é¢ãã確èªãéä¿¡ããŸãã ãããã¯ãŒã¯ãã¬ã·ãŒããŒãã³ã¬ã¯ã¿ãŒã«é害ãçºçããå ŽåãæåŸã®è¡ã2å以äžé ä¿¡ã§ããŸãã ä¿èšŒã ãã§ãªãã1åéãã®é ä¿¡ãå¿ èŠãªå Žåã¯ãYandexãæ§ç¯ããã¯ããã«è€éãªã·ã¹ãã habrahabr.ru/company/yandex/blog/239823ã«ã€ããŠèªãããšãã§ããŸãã
åã ã®ã¯ã©ã¹ã®ãã¹ãããã«ãé ä¿¡
æ¢ã«è¿°ã¹ãããã«ã1ã€ã®éåžžã«ã倧éã®ãã¹ã¯ãªããã垯åå¹ ãå®å šã«ãããã¯ããä»ã®ãã¹ãŠã®ãã°ã®åŠçãé ãããå¯èœæ§ãããããšã«æºè¶³ããŠããŸããã§ããã ããã¯ãã¹ã¯ã©ã€ããã¬ã·ãŒããŒãžã®é ä¿¡ãçºçãããããã¯ããã«éãæžã蟌ãããšãã§ããå°ãªããšãåããžã§ãå ã§ãã°å ã®è¡ã®ã·ãŒã±ã³ã¹ã«åŸãå¿ èŠããããããã¹ã¯ã©ã€ãããã®ã€ãã³ãã®åŠçãã·ã³ã°ã«ã¹ã¬ããã§ãã£ãããã«çºçããŸããã
ãã®åé¡ã®è§£æ±ºçã¯éåžžã«ç°¡åã§ããããã«ãã¿ã¹ã¯åŠçã®æ··éãã«é¡äŒŒãããã®ãäœæããå¿ èŠããããŸãã 1ã€ã®ãã¹ã§ããã¡ã€ã«å ã®Nè¡ä»¥äžãåŠçããŠããã次ã®è¡ã«é²ã¿ãŸãã ãéåžžã®ããã°çšã«éä¿¡ããããã¹ãŠã®æçããµãŒããŒã§åä¿¡ããããšãã倪åãã¡ã€ã«ãã®éä¿¡ã«æ»ããåãã¢ã«ãŽãªãºã ã§åäœã§ããŸãã ãããã£ãŠãã倧ããªãã¡ã€ã«ãã®é ä¿¡ã¯ã·ã¹ãã ã«éå®çãªåœ±é¿ãåãŒããŸããæ®ãã®ãã¹ãŠã®ã¯ã©ã¹ã®ãã°ã¯ãæ倧ãã±ãããµã€ãºNã«ãã£ãŠèŠå¶ãããäžå®ã®é 延ã§é ä¿¡ããç¶ããŸããã§ããã ãæ©ãé ä¿¡ãããŸãã
ãã¡ã€ã«ã®å転
ãã°ãæéã®çµéãšãšãã«ãµãŒããŒäžã®ãã¹ãŠã®ã¹ããŒã¹ãå æããªãããã«ããã«ã¯ããã°ãããŒããŒã·ã§ã³ããå¿ èŠããããŸãã ãã°ããŒããŒã·ã§ã³ã¯ãæãå€ããã°ãã¡ã€ã«ãåé€ããããæ°ãããã¡ã€ã«ã®ååããå€ãããã¡ã€ã«ã«å€æŽããããã»ã¹ã§ãã ãã®å ŽåãããŒããŒã·ã§ã³ãšã¯ãå€ããã°ãã¡ã€ã«ãåé€ããçŸåšã®ãã°ãã¡ã€ã«ã®ååãå€æŽããããšã§ãïŒclass_name.out.log-> class_name.out.log.oldïŒã ãã¡ã€ã«ã®ååãå€æŽãããšãããã®ãã¡ã€ã«ãéãããŸãŸã«ãããã¹ãŠã®ããã»ã¹ã¯ããã¡ã€ã«ã®åŠçãç¶è¡ã§ããŸãïŒãã®å Žåã¯æžã蟌ã¿ïŒã ãããã£ãŠãæ°ãããã°ãã¡ã€ã«ãšå€ããã°ãã¡ã€ã«ã®äž¡æ¹ã§çºçããå€æŽãåŒãç¶ãéä¿¡ããå¿ èŠããããŸãã ãã¡ã€ã«ã®ååãå€æŽãããšãiããŒããä¿åããããããããŒã¿ããŒã¹ã«ã¯ããã¡ã€ã«åã§ã¯ãªãiããŒãå°çšã®æ£åžžã«éä¿¡ããããªãã»ãããããŒã¿ããŒã¹ã«ä¿åãããŸãã
ããŒããŒã·ã§ã³ã«é¢é£ãããã1ã€ã®å°ããªåé¡ã¯ããã¡ã€ã«ãåé€ããåã«ãä»ã®ãŠãŒã¶ãŒããã®ãã¡ã€ã«ã«æžã蟌ãŸãªãããšãäœããã®æ¹æ³ã§å€æããå¿ èŠãããããšã§ãã ãã¹ãŠã®ã¢ããªã±ãŒã·ã§ã³ã¯flockïŒïŒã䜿çšããã«O_APPENDãã©ã°ã䜿çšããŠãã¡ã€ã«ã«æžã蟌ããããä»ã®ç®çã§flockïŒïŒã䜿çšã§ããŸãã ãã®å Žåãã¢ããªã±ãŒã·ã§ã³ã¯ãäœæ¥ãéå§ããåã«æžã蟌ããã¡ã€ã«èšè¿°åã«å¯ŸããŠå ±æããã¯ïŒLOCK_SHïŒãååŸããŸãã ãã¡ã€ã«ã䜿çšãããªããªã£ãããšã確èªããã«ã¯ãæä»ããã¯ïŒLOCK_EXïŒãååŸããå¿ èŠããããŸãã ããã¯ãååŸã§ããå Žåããã¡ã€ã«ã¯äœ¿çšãããªããªããåé€ã§ããŸãã ãã以å€ã®å Žåã¯ããã°ãã¡ã€ã«ã解æŸããããŸã§åŸ æ©ããäžæçã«ããŒããŒã·ã§ã³ãé ãããå¿ èŠããããŸãã
ããã©ãŒãã³ã¹ãçµè«
ãã°ã³ã¬ã¯ã¿ãŒã®ä»¥åã®ããŒãžã§ã³ã¯ã·ã³ã°ã«ã¹ã¬ããã§åäœããPHPã§èšè¿°ãããŠãããããæ¯èŒã¯ããŸãæ£çŽã§ã¯ãããŸããã ããã§ããå€ãã¢ãŒããã¯ãã£ãšæ°ããã¢ãŒããã¯ãã£ã®äž¡æ¹ã®çµæãæ瀺ããããšæããŸãã
å€ãã·ã¹ãã ïŒPHPã1ã€ã®ã¹ããªãŒã ïŒ-ãµãŒããŒããã3 MiB / s-ã¯PHPã«ãšã£ãŠãŸãšããªçµæã§ãã
æ°ããã·ã¹ãã ïŒGoãå®å šéåæããã³ãã«ãã¹ã¬ããïŒ-ãµãŒããŒããã100 MiB / s-ã¯ãããã¯ãŒã¯ã«ãŒããšãã©ã€ãäžã«ãããŸãã
ãã°ã¢ã»ã³ããªã·ã¹ãã ã®å€æŽã®çµæãã·ã¹ãã ã«ãã£ããã¹ãŠã®åé¡ã解決ããé ä¿¡é床ã«å€§ããªããŒãžã³ããããããŸããããŸããåã ã®ã¯ã©ã¹ã®ã措氎ãã«å¯Ÿããèæ§ãç²åŸããŸããã ã , , Go , .
åç §è³æ
Open-source : github.com/badoo/thunder
open-source : tech.badoo.com/open-source
youROCK
Lead PHP developer