diff options
| author | Steve Kemp <steve@steve.org.uk> | 2013-01-12 14:54:02 +0000 | 
|---|---|---|
| committer | Steve Kemp <steve@steve.org.uk> | 2013-01-12 14:54:02 +0000 | 
| commit | d8681e42cb299defa66fccb0ce04a25911d80ed9 (patch) | |
| tree | b6aba49f876cca51cbe453fbc20bc09aa0115785 /bytemark | |
| parent | 5c1494a0e902e103d52f8926ea77cb1f3a7e689d (diff) | |
  Initial implementation.
Diffstat (limited to 'bytemark')
| -rwxr-xr-x | bytemark/bin/custodian-instances | 233 | 
1 files changed, 233 insertions, 0 deletions
| diff --git a/bytemark/bin/custodian-instances b/bytemark/bin/custodian-instances new file mode 100755 index 0000000..8b8043e --- /dev/null +++ b/bytemark/bin/custodian-instances @@ -0,0 +1,233 @@ +#!/usr/bin/ruby1.8 +# +#  Add/Remove/List custodian workers +# +# Steve +# -- + + + +require 'etc' +require 'fileutils' +require 'getoptlong' + + + + +# +#  A single worker instance. +# +class CustodianWorker + +  attr_reader :path + +  # +  # Constructor. +  # +  # Called with the path to a service directory. +  # +  def initialize( path ) +    @path = path +  end + + +  # +  #  Does the service directory look like a worker? +  # +  def is_worker? + +    # the directory must exist. +    return false unless( File.directory?( @path ) ) + +    # There should be a ./run file in the directory. +    return false unless( File.executable?( "#{@path}/run" ) ) + +    # The run-file should invoke custodian-dequeue. +    contents = read_file( "#{@path}/run" ) +    if ( contents !~ /exec su - ([\S]+)(.*)exec custodian-dequeue/ ) +      return false +    end + +    # The name must be custodian-$LOGIN +    if ( @path =~ /custodian-([.*])$/ ) +      user = $1.dup + +      data = Etc.getpwnam( user ) +      return false unless( data.name ) +      return false unless( File.directory?( data.dir ) ) +    end +    true +  end + + + +  # +  #  Create a new worker-service. +  # +  def CustodianWorker.create( login ) + +    # +    #  Does the service directory already exist? +    # +    sv =  "/etc/service/custodian-#{login}" +    if ( File.directory?( sv ) ) +      puts "Target already exists: #{sv}" +      exit( 1 ) +    end + +    # +    #  Does the user exist? +    # +    begin +      data = Etc.getpwnam( login ) +      if ( login.name ) +        puts "Unix user already exists: #{login}" +        exit( 1 ) +      end +    rescue => ex +    end + +    # +    #  Create the directory +    # +    FileUtils.mkdir_p( sv ) + +    # +    #  Add the unix user. +    # +    system( "useradd --create-home #{login}" ) + +    # +    #  Create the run-script. +    # +    File.open( "#{sv}/run", "w" ) do |fh| +      fh.puts <<EOF +#!/bin/sh +exec su - #{login} -c "exec custodian-dequeue --verbose" +EOF +    end + +    File.chmod( 0755, "#{sv}/run" ) +  end + + + + +  # +  # Delete an existing worker service. +  # +  def CustodianWorker.delete( login ) + +    # +    #  Stop the service +    # +    sv =  "/etc/service/custodian-#{login}" +    if ( File.directory?( sv ) ) +      puts "Stopping service: #{sv}" +      system( "sv down #{sv}" ) +    end + +    # +    #  Delete the user +    # +    begin +      data = Etc.getpwnam( login ) +      if ( data.name ) +        system( "userdel #{login}" ) +        if ( ( File.directory?( data.dir ) ) && ( data.dir == "/home/#{login}" ) ) +          puts "Removing home directory" +          system( "rm -rf #{data.dir}" ) +        end +      end +    rescue => ex +       puts "WARNING: Login not found #{login}" +    end + +    # +    #  Remove the service +    # +    if ( File.directory?( sv ) ) +        puts "Removing service" +        system( "rm -rf #{sv}" ) +    end +  end + + +  # +  # Return a string containing the given file contents. +  # +  def read_file( fname ) +    lines = File.open( fname, 'r') {|file| file.readlines.collect} +    lines.join( "\n" ) +  end + + +end + + + +# +#  Get access to custodian services +# +class CustodianServices + +  # +  # The name for this instance. +  # +  attr_reader :prefix + +  # +  # Constructor +  # +  def initialize( prefix = "/etc/service" ) +    @prefix = prefix +  end + +  # +  #  Return an array of all services which are custodian-workers +  # +  def get +    a = Array.new() + +    Dir.entries( @prefix ).sort_by{|s| s.scan(/\d+/).map{|s| s.to_i}}.each do |name| +      tmp = CustodianWorker.new( "#{@prefix}/#{name}" ) +      a.push( tmp ) if ( tmp.is_worker? ) +    end + +    a +  end + +end + + + +if __FILE__ == $0 then + + +  arg = ARGV.shift || "list"; + +  case arg +  when "list" +    helper = CustodianServices.new(); +    helper.get().each do |f| +      puts f.path +    end +  when "add" +    name = ARGV.shift || nil +    if ( name.nil? ) +      puts "Usage: $0 add NAME" +      exit 1 +    end +    f = CustodianWorker.create( name ) +  when "delete" +    name = ARGV.shift || nil +    if ( name.nil? ) +      puts "Usage: $0 delete NAME" +      exit 1 +    end +    f = CustodianWorker.delete( name ) +  else +    puts "Unknown argument.  Usage $0 [add|delete|list]" +  end +end + | 
