Guard: ๊ธฐ๊ธฐ์— ๋‚จ์€ ๊ณต๊ฐ„์ด ์—†์Šต๋‹ˆ๋‹ค. ์‹œ์ฒญํ•˜์ง€ ๋ชปํ–ˆ์Šต๋‹ˆ๋‹ค...

์— ๋งŒ๋“  2012๋…„ 01์›” 22์ผ  ยท  18์ฝ”๋ฉ˜ํŠธ  ยท  ์ถœ์ฒ˜: guard/guard

๊ฐ€๋“œํŒŒ์ผ:

guard 'rspec', :version => 2, :cli => "--color --format nested" do
  watch(%r{^spec/.+_spec\.rb})
  watch(%r{^lib/(.+)\.rb})     { |m| "spec/#{m[1]}_spec.rb" }
end

์ ฌํŒŒ์ผ

group :development do
  gem 'guard'
  gem 'libnotify'
  gem 'guard-rspec'
  gem 'rb-readline'
end

ํ™˜๊ฒฝ

  • ๋ฆฌ๋ˆ…์Šค 2.6.32-5-amd64
  • ๋ฃจ๋น„ 1.8.7 (2011-06-30 ํŒจ์น˜ ๋ ˆ๋ฒจ 352)

    ์˜ค๋ฅ˜

guard start ์‹คํ–‰ํ•˜๋ฉด ๋ณด๊ณ ์„œ์™€ ํ•จ๊ป˜ libnotify ๋ฉ”์‹œ์ง€๊ฐ€ ํ‘œ์‹œ๋˜๊ณ  ๋‹ค์Œ ์˜ค๋ฅ˜์™€ ํ•จ๊ป˜ ๊ฐ€๋“œ ์ถฉ๋Œ์ด ๋ฐœ์ƒํ•ฉ๋‹ˆ๋‹ค.

//home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/watcher.rb:80:in `initialize': No space left on device - Failed to watch "/home/blake/dev/my/project_child/.git/objects/78": The user limit on the total number of inotify watches was reached or the kernel failed to allocate a needed resource. (Errno::ENOSPC)
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:190:in `new'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:190:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:199:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:195:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:192:in `each'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:192:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:195:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:192:in `each'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:192:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:195:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:192:in `each'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:192:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/guard/listeners/linux.rb:58:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/guard/listener.rb:100:in `start'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/guard/listeners/linux.rb:20:in `start'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/guard.rb:203:in `start'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/guard/cli.rb:75:in `start'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/thor-0.14.6/lib/thor/task.rb:22:in `send'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/thor-0.14.6/lib/thor/task.rb:22:in `run'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/thor-0.14.6/lib/thor/invocation.rb:118:in `invoke_task'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/thor-0.14.6/lib/thor.rb:263:in `dispatch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/thor-0.14.6/lib/thor/base.rb:389:in `start'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/bin/guard:6
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/bin/guard:19:in `load'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/bin/guard:19home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/watcher.rb:80:in `initialize': No space left on device - Failed to watch "/home/blake/dev/my/project_child/.git/objects/78": The user limit on the total number of inotify watches was reached or the kernel failed to allocate a needed resource. (Errno::ENOSPC)
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:190:in `new'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:190:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:199:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:195:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:192:in `each'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:192:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:195:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:192:in `each'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:192:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:195:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:192:in `each'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/vendor/linux/lib/rb-inotify/notifier.rb:192:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/guard/listeners/linux.rb:58:in `watch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/guard/listener.rb:100:in `start'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/guard/listeners/linux.rb:20:in `start'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/guard.rb:203:in `start'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/lib/guard/cli.rb:75:in `start'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/thor-0.14.6/lib/thor/task.rb:22:in `send'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/thor-0.14.6/lib/thor/task.rb:22:in `run'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/thor-0.14.6/lib/thor/invocation.rb:118:in `invoke_task'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/thor-0.14.6/lib/thor.rb:263:in `dispatch'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/thor-0.14.6/lib/thor/base.rb:389:in `start'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/gems/guard-1.0.0/bin/guard:6
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/bin/guard:19:in `load'
    from /home/blake/.rvm/gems/ruby-1.8.7-p352@project/bin/guard:19


git ํŒŒ์ผ์„ ๋ณด๋ ค๊ณ  ํ•ฉ๋‹ˆ๊นŒ? ๋ญ”๊ฐ€ ๊ทธ๋ฆฌ์›Œ?

๊ฐ€์žฅ ์œ ์šฉํ•œ ๋Œ“๊ธ€

inotify์— ๋Œ€ํ•œ max_user_watches๋ฅผ ๋Š˜๋ ค๋ณด์‹ญ์‹œ์˜ค. ๊ธฐ๋ณธ๊ฐ’์€ 8192๋กœ ์„ค์ •๋˜์–ด ์žˆ์Šต๋‹ˆ๋‹ค. 100k๋กœ ์„ค์ •ํ–ˆ๋Š”๋ฐ ๋ฌธ์ œ๊ฐ€ ์—†์Šต๋‹ˆ๋‹ค.

cat /proc/sys/fs/inotify/max_user_watches

echo 100000|sudo tee /proc/sys/fs/inotify/max_user_watches

๋ถ€ํŒ… ์‹œ max_user_watches๋ฅผ ๋Š˜๋ฆฌ๋ ค๋ฉด /etc/sysctl.conf๋ฅผ ํŽธ์ง‘ํ•˜๊ณ  fs.inotify.max_user_watches=100000์„ ์ถ”๊ฐ€ํ•˜๊ฑฐ๋‚˜ fs.inotify.max_user_watches=๋ฅผ 100000์œผ๋กœ ์ˆ˜์ •ํ•ฉ๋‹ˆ๋‹ค.

๋‚˜์—๊ฒŒ ๊ฐ์‚ฌํ•˜์ง€ ๋ง๊ณ  ์ด ์‚ฌ๋žŒ์—๊ฒŒ ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค -> http://blog.sorah.jp/2012/01/24/inotify-limitation

๋ชจ๋“  18 ๋Œ“๊ธ€

์ด๊ฒƒ์€ ํด๋”์— ๋ณผ ํŒŒ์ผ์ด ๋„ˆ๋ฌด ๋งŽ์„ ๋•Œ ๋„์ฐฉํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ignore_paths ๋ฉ”์„œ๋“œ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์ผ๋ถ€ ๊ฒฝ๋กœ๋ฅผ ๋ฌด์‹œํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค(์ž์„ธํ•œ ๋‚ด์šฉ์€ README ์ฐธ์กฐ ).

ignore_paths '.git' ์‚ฌ์šฉํ•ด ๋ณด์•˜๋Š”๋ฐ ํšจ๊ณผ๊ฐ€ ์—†์—ˆ์Šต๋‹ˆ๋‹ค.

ํ”„๋กœ์ ํŠธ์— 93๊ฐœ์˜ ํŒŒ์ผ๋งŒ ์žˆ์Šต๋‹ˆ๋‹ค.

find . | grep -v '.git'  | wc -l
93

์ด์ƒํ•ฉ๋‹ˆ๋‹ค. lib notify์—๊ฒŒ ๋ฌผ์–ด๋ณด์‹ญ์‹œ์˜ค.

์ฐธ๊ณ ๋กœ .git ๋Š” ๊ธฐ๋ณธ์ ์œผ๋กœ ์ด๋ฏธ ๋ฌด์‹œ๋ฉ๋‹ˆ๋‹ค. https://github.com/guard/guard/blob/master/lib/guard/listener.rb#L19

์†Œ์‹์ด ์žˆ๋‚˜์š”?

์•„๋‹ˆ์š”. ๋‹ค๋ฅธ ์ปดํ“จํ„ฐ์—์„œ ์‹คํ–‰ํ•˜๋ ค๊ณ  ํ•ฉ๋‹ˆ๋‹ค.

ํ .. ์ œ ์ž‘์—…์—์„œ๋Š” ๋‹ค๋ฅธ PC์—์„œ ๋™์ผํ•œ ํ”„๋กœ์ ํŠธ๊ฐ€ ๊ฐ€๋“œ๋กœ ์ž˜ ์‹คํ–‰๋ฉ๋‹ˆ๋‹ค. ๋‘ PC์—์„œ ์ €๋Š” Debian Squeeze๋ฅผ ์‚ฌ์šฉํ•ฉ๋‹ˆ๋‹ค.

ignore_paths๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋ฌด์‹œํ–ˆ๋˜ ํฐ ๋””๋ ‰ํ† ๋ฆฌ์— ๋น„์Šทํ•œ ๋ฌธ์ œ๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค. ๋ฌด์‹œ๋œ ๋””๋ ‰ํ† ๋ฆฌ์— ์ผ๋ถ€ ํŒŒ์ผ์ด '๊ฐ์‹œ ์‹คํŒจ'ํ–ˆ๋‹ค๊ณ  ๋ถˆํ‰์„ ๊ณ„์†ํ•ฉ๋‹ˆ๋‹ค.

๊ฒฝ๋กœ๋Š” Guard ์ˆ˜์ค€์—์„œ๋งŒ ๋ฌด์‹œ๋˜์ง€๋งŒ rb-inotify ์—์„œ๋Š” ๋ฌด์‹œ๋˜์ง€ ์•Š์œผ๋ฏ€๋กœ ignore_paths ๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์€ ์—ฌ๊ธฐ์—์„œ ์œ ์šฉํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•˜๋ ค๋ฉด rb-inotify ignore_paths ์˜ต์…˜์ด ํ•„์š”ํ•˜๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค. @nex3 ๊ทธ๊ฒŒ ๊ฐ€๋Šฅํ•  ๊ฒƒ

๊ธฐ๋ณธ inotify ์ธํ„ฐํŽ˜์ด์Šค์—์„œ ๊ฒฝ๋กœ๋ฅผ ์„ ํƒ์ ์œผ๋กœ ๋ฌด์‹œํ•˜๋Š” ๋ฐฉ๋ฒ•์€ ์—†๋Š” ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค.

์ง€๊ธˆ์€ ํ”„๋กœ์ ํŠธ ํŠธ๋ฆฌ์—์„œ ๋ชฌ์Šคํ„ฐ ๋””๋ ‰ํ† ๋ฆฌ๋ฅผ ๊ฐ€์ ธ์™”์Šต๋‹ˆ๋‹ค. ์‹œ๋„ํ•ด ์ฃผ์…”์„œ ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค.

.git ๋””๋ ‰ํ† ๋ฆฌ๋ฅผ ์ œ๊ฑฐํ–ˆ๋Š”๋ฐ ์ €์—๊ฒŒ๋„ ํšจ๊ณผ์ ์ž…๋‹ˆ๋‹ค. ํ•˜์ง€๋งŒ ๋” ์ข‹์€ ๊ฒƒ์ด ์žˆ์„ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. :)

inotify์— ๋Œ€ํ•œ max_user_watches๋ฅผ ๋Š˜๋ ค๋ณด์‹ญ์‹œ์˜ค. ๊ธฐ๋ณธ๊ฐ’์€ 8192๋กœ ์„ค์ •๋˜์–ด ์žˆ์Šต๋‹ˆ๋‹ค. 100k๋กœ ์„ค์ •ํ–ˆ๋Š”๋ฐ ๋ฌธ์ œ๊ฐ€ ์—†์Šต๋‹ˆ๋‹ค.

cat /proc/sys/fs/inotify/max_user_watches

echo 100000|sudo tee /proc/sys/fs/inotify/max_user_watches

๋ถ€ํŒ… ์‹œ max_user_watches๋ฅผ ๋Š˜๋ฆฌ๋ ค๋ฉด /etc/sysctl.conf๋ฅผ ํŽธ์ง‘ํ•˜๊ณ  fs.inotify.max_user_watches=100000์„ ์ถ”๊ฐ€ํ•˜๊ฑฐ๋‚˜ fs.inotify.max_user_watches=๋ฅผ 100000์œผ๋กœ ์ˆ˜์ •ํ•ฉ๋‹ˆ๋‹ค.

๋‚˜์—๊ฒŒ ๊ฐ์‚ฌํ•˜์ง€ ๋ง๊ณ  ์ด ์‚ฌ๋žŒ์—๊ฒŒ ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค -> http://blog.sorah.jp/2012/01/24/inotify-limitation

@jhirn ์ข‹์€ ๋งํฌ, ๊ณต์œ ํ•ด ์ฃผ์…”์„œ ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค! /cc @Maher4Ever

@thibaudgg ์‚ฌ์šฉ์ž๋ฅผ ๋•๊ธฐ ์œ„ํ•ด ์ด ์˜ˆ์™ธ๋ฅผ ํฌ์ฐฉํ•˜๊ณ  (์œ„ํ‚ค ํŽ˜์ด์ง€?) ๋˜๋Š” Listen ๋ฆฌํฌ์ง€ํ† ๋ฆฌ์— ์žˆ๋Š” ๋ฌด์–ธ๊ฐ€์— ๋Œ€ํ•œ ๋งํฌ๋ฅผ ํ‘œ์‹œํ•˜๋Š” ๊ฒƒ์ด ์ •๋ง ์ข‹์€ ์ƒ๊ฐ์ด๋ผ๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค. Listen ์— ์ฒซ ๋ฒˆ์งธ ์œ„ํ‚ค ํŽ˜์ด์ง€๋ฅผ ์ถ”๊ฐ€ํ•ด ๋ณผ๊นŒ์š”? :)

๊ทธ๋ ‡๊ฒŒ ํ•˜์„ธ์š”. ํ•˜์ง€๋งŒ ์ € ๋ง๊ณ  github.com/sorah์˜ ํฌ๋ ˆ๋”ง์„ ์‚ฌ์šฉํ•˜์„ธ์š”. =)

@Maher4Ever yes ์ฒซ ๋ฒˆ์งธ Listen Wiki ํŽ˜์ด์ง€์— ๋Œ€ํ•œ ๋งํฌ์— +1!

@jhirn , ์ž˜ ์ฐพ์•˜์Šต๋‹ˆ๋‹ค!
@thibaudgg , ์ง€์›์— ๊ฐ์‚ฌ๋“œ๋ฆฝ๋‹ˆ๋‹ค.

์ด ํŽ˜์ด์ง€๊ฐ€ ๋„์›€์ด ๋˜์—ˆ๋‚˜์š”?
0 / 5 - 0 ๋“ฑ๊ธ‰