lsbservice to_xml now
[opensuse:yast-rest-service.git] / yast-api / lib / lsbservice.rb
1 #
2 # This provides generic functions for
3 # LSB compatible services
4 #
5 #
6 #
7 class Lsbservice
8   PREFIX = '/etc/init.d/'
9   
10   #
11   # iterates over all service names
12   #
13   def self.each
14 #    Dir.entries(PREFIX).each do |d|
15      ["cron", "cups", "gpm", "ntp", "random", "smbfs", "sshd" ].each do |d|
16       next if d[0,1] == '.'
17       next if d == "README"
18       next if File.directory?( PREFIX+d )
19       yield d
20     end
21   end
22     
23   #
24   # Lsbservice.all -> Array of string
25   #  returns array of all available services
26   #
27   
28   def Lsbservice.all
29     result = []
30     Lsbservice::each do |d|
31       result << d
32     end
33     result
34   end
35
36   # 0 - success
37   # 1 - generic or unspecified error
38   # 2 - invalid or excess argument(s)
39   # 3 - unimplemented feature (e.g. "reload")
40   # 4 - insufficient privilege
41   # 5 - program is not installed
42   # 6 - program is not configured
43   # 7 - program is not running
44   @@states = [ :success, :error, :badargs, :unimplemented, :noperm, :notinstalled, :notconfigured, :notrunning ]
45   
46   #
47   # Lsbservice.new name
48   #   Creates a new instance of Lsbservice for service <name>
49   #
50   # Attributes
51   #  name: name of the service
52   #  path: path to init script
53   #  functions: available functions as array of strings, typically "start", "stop", ...
54   #
55   
56   attr_reader :name, :path, :functions
57   
58   def initialize name
59     name = name.to_s unless name.is_a? String
60     @name = name
61     @functions = []
62     @path = PREFIX+name
63
64     raise "Unexisting service" unless File.exists?( path )
65     
66     if File.executable?( path )
67       # run init script to get its 'Usage' line
68       IO.popen( path, 'r+' ) do |pipe|
69         loop do
70           break if pipe.eof?
71           l = pipe.read
72           case l
73           when /Usage:\s*(\S*)\s*\{([^\}]*)\}/
74             #     STDERR.puts "USAGE: #{$1}, #{$2}"
75             @path = $1
76             @functions = $2.split "|"
77             break
78           end
79         end
80       end
81     end
82   end
83   
84   def method_missing( method, *args )
85     raise "Unknown method #{method}" unless @functions.include?( method.to_s )
86     puts "Running '#{@path} #{method}'"
87     system("#{@path} #{method} #{args.join(' ')} > /dev/null 2>&1")
88     puts "Returned #{$?.class}, #{$?.inspect}, #{$?.exitstatus}"
89     s = $?.exitstatus
90     return @@states[ s ] if s < @@states.size
91     :unknown
92   end
93   
94   #
95   # See 'The Rails Way', page 510
96   #
97   
98   def to_xml( options = {} )
99     STDERR.puts "#{self}.to_xml"
100     xml = options[:builder] ||= Builder::XmlMarkup.new(options)
101     xml.instruct! unless options[:skip_instruct]
102     xml.service do
103       xml.tag!(:name, @name )
104       xml.tag!(:path, @path )
105       xml.links do
106         @functions.each do |f|
107           xml.tag!(f.to_sym, @name+"/"+f)
108         end
109       end
110     end  
111   end
112 end