diff options
author | luke <luke@980ebf18-57e1-0310-9a29-db15c13687c0> | 2006-04-11 23:00:29 +0000 |
---|---|---|
committer | luke <luke@980ebf18-57e1-0310-9a29-db15c13687c0> | 2006-04-11 23:00:29 +0000 |
commit | cd9ea8056a71279aab384d204d90e24236e7ae57 (patch) | |
tree | 21c805a6a9da53b90809566816130ac13540edae /lib | |
parent | 71793fb3d096b74977b73fffe16bbeb8f45c94b9 (diff) | |
download | puppet-cd9ea8056a71279aab384d204d90e24236e7ae57.tar.gz puppet-cd9ea8056a71279aab384d204d90e24236e7ae57.tar.xz puppet-cd9ea8056a71279aab384d204d90e24236e7ae57.zip |
Adding locking to the master client, so that only one copy of puppetd will be running. This should make it safe to run puppetd manually while it is also running normally.
git-svn-id: https://reductivelabs.com/svn/puppet/trunk@1107 980ebf18-57e1-0310-9a29-db15c13687c0
Diffstat (limited to 'lib')
-rw-r--r-- | lib/puppet/client/master.rb | 86 |
1 files changed, 67 insertions, 19 deletions
diff --git a/lib/puppet/client/master.rb b/lib/puppet/client/master.rb index 1da921aa4..d3e7d2e8a 100644 --- a/lib/puppet/client/master.rb +++ b/lib/puppet/client/master.rb @@ -1,5 +1,9 @@ # The client for interacting with the puppetmaster config server. +require 'sync' + class Puppet::Client::MasterClient < Puppet::Client + @@sync = Sync.new + Puppet.setdefaults("puppetd", :puppetdlockfile => [ "$statedir/puppetdlock", "A lock file to temporarily stop puppetd from doing anything."], @@ -95,15 +99,19 @@ class Puppet::Client::MasterClient < Puppet::Client @cachefile end - # Disable running the configuration. - def disable - Puppet.notice "Disabling puppetd" + # Disable running the configuration. This can be used from the command line, but + # is also used to make sure only one client is running at a time. + def disable(running = false) + text = nil + if running + text = Process.pid + else + text = "" + Puppet.notice "Disabling puppetd" + end Puppet.config.use(:puppet) - #unless FileTest.exists? File.dirname(Puppet[:puppetdlockfile]) - # Puppet.recmkdir(File.dirname(Puppet[:puppetdlockfile])) - #end begin - File.open(Puppet[:puppetdlockfile], "w") { |f| f.puts ""; f.flush } + File.open(Puppet[:puppetdlockfile], "w") { |f| f.puts text } rescue => detail raise Puppet::Error, "Could not lock puppetd: %s" % detail end @@ -126,9 +134,12 @@ class Puppet::Client::MasterClient < Puppet::Client end end - # Enable running again. - def enable - Puppet.notice "Enabling puppetd" + # Enable running again. This can be used from the command line, but + # is also used to make sure only one client is running at a time. + def enable(running = false) + unless running + Puppet.notice "Enabling puppetd" + end if FileTest.exists? Puppet[:puppetdlockfile] File.unlink(Puppet[:puppetdlockfile]) end @@ -259,6 +270,37 @@ class Puppet::Client::MasterClient < Puppet::Client return @objects end + # Make sure only one client runs at a time, and make sure only one thread + # runs at a time. However, this does not lock local clients -- you could have + # as many separate puppet scripts running as you want. + def lock + if @local + yield + else + @@sync.synchronize(Sync::EX) do + disable(true) + begin + yield + ensure + enable(true) + end + end + end + end + + def locked? + if FileTest.exists? Puppet[:puppetdlockfile] + text = File.read(Puppet[:puppetdlockfile]).chomp + if text =~ /\d+/ + return text + else + return true + end + else + return false + end + end + # Retrieve the cached config def retrievecache if FileTest.exists?(self.cachefile) @@ -270,18 +312,24 @@ class Puppet::Client::MasterClient < Puppet::Client # The code that actually runs the configuration. def run - if FileTest.exists? Puppet[:puppetdlockfile] - Puppet.notice "%s exists; skipping configuration run" % + if pid = locked? + t = "" + if pid == true + PUppet.notice "Locked by process %s" % pid + end + Puppet.notice "Lock file %s exists; skipping configuration run" % Puppet[:puppetdlockfile] else - self.getconfig + lock do + self.getconfig - if defined? @objects and @objects - unless @local - Puppet.notice "Starting configuration run" - end - benchmark(:notice, "Finished configuration run") do - self.apply + if defined? @objects and @objects + unless @local + Puppet.notice "Starting configuration run" + end + benchmark(:notice, "Finished configuration run") do + self.apply + end end end end |