summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDarryl L. Pierce <dpierce@redhat.com>2008-10-10 15:44:43 -0400
committerDarryl L. Pierce <dpierce@redhat.com>2008-10-10 15:54:00 -0400
commit42f0c966b0ca1d658d8f06dea06cee83f02fec7a (patch)
treed330db1ed3a4c42f948a20010346fdf0782a9edc
parentaa6b0644de09f741cc0fa77d6a95bf61d8f6a05b (diff)
downloadcobbler-42f0c966b0ca1d658d8f06dea06cee83f02fec7a.tar.gz
cobbler-42f0c966b0ca1d658d8f06dea06cee83f02fec7a.tar.xz
cobbler-42f0c966b0ca1d658d8f06dea06cee83f02fec7a.zip
Added support for image-based systems.
Also refactored the metaprogramming to fix a nil bug that surfaced.
-rw-r--r--contrib/ruby/ChangeLog3
-rw-r--r--contrib/ruby/Rakefile2
-rw-r--r--contrib/ruby/lib/cobbler/base.rb148
-rw-r--r--contrib/ruby/lib/cobbler/distro.rb2
-rw-r--r--contrib/ruby/lib/cobbler/image.rb2
-rw-r--r--contrib/ruby/lib/cobbler/network_interface.rb2
-rw-r--r--contrib/ruby/lib/cobbler/profile.rb2
-rw-r--r--contrib/ruby/lib/cobbler/system.rb8
-rw-r--r--contrib/ruby/test/test_system.rb30
9 files changed, 99 insertions, 100 deletions
diff --git a/contrib/ruby/ChangeLog b/contrib/ruby/ChangeLog
index 4acbb71b..aaebf322 100644
--- a/contrib/ruby/ChangeLog
+++ b/contrib/ruby/ChangeLog
@@ -1,3 +1,6 @@
+* Fri Oct 10 2008 Darryl Pierce <dpierce@redhat.com> - 0.1.1-1
+- Added support for image-based systems.
+
* Mon Sep 08 2008 Darryl Pierce <dpierce@redhat.com> - 0.1.0-1
- First official build for Fedora.
diff --git a/contrib/ruby/Rakefile b/contrib/ruby/Rakefile
index 0d58ce68..b0e4e509 100644
--- a/contrib/ruby/Rakefile
+++ b/contrib/ruby/Rakefile
@@ -22,7 +22,7 @@ require 'rake/testtask'
require 'rake/gempackagetask'
PKG_NAME='rubygem-cobbler'
-PKG_VERSION='0.1.0'
+PKG_VERSION='0.1.1'
PKG_FILES=FileList[
'Rakefile', 'README', 'ChangeLog', 'COPYING', 'NEWS', 'TODO',
'lib/**/*.rb',
diff --git a/contrib/ruby/lib/cobbler/base.rb b/contrib/ruby/lib/cobbler/base.rb
index 34fc5f17..f1464a5a 100644
--- a/contrib/ruby/lib/cobbler/base.rb
+++ b/contrib/ruby/lib/cobbler/base.rb
@@ -1,13 +1,13 @@
#
# base.rb
-#
+#
# Copyright (C) 2008 Red Hat, Inc.
# Written by Darryl L. Pierce <dpierce@redhat.com>
#
# This file is part of rubygem-cobbler.
#
# rubygem-cobbleris free software: you can redistribute it and/or modify
-# it under the terms of the GNU Lesser General Public License as published
+# it under the terms of the GNU Lesser General Public License as published
# by the Free Software Foundation, either version 2.1 of the License, or
# (at your option) any later version.
#
@@ -19,137 +19,125 @@
# You should have received a copy of the GNU General Public License
# along with rubygem-cobbler. If not, see <http://www.gnu.org/licenses/>.
#
-
+
require 'xmlrpc/client'
require 'pp'
require 'yaml'
module Cobbler
include XMLRPC
-
+
# +Base+ represents a remote Cobbler server.
- #
- # Child classes can define fields that will be retrieved from Cobbler by
+ #
+ # Child classes can define fields that will be retrieved from Cobbler by
# using the +cobbler_field+ method. For example:
- #
+ #
# class System < Base
# cobbler_lifecycle :find_all => 'get_systems'
# cobbler_field :name
# cobbler_collection :owners, :type => 'String', :packing => :hash
# end
- #
- # declares a class named System that contains two fields and a class-level
+ #
+ # declares a class named System that contains two fields and a class-level
# method.
- #
- # The first field, "name", is a simple property. It will be retrieved from
- # the value "name" in the remote definition for a system, identifyed by the
+ #
+ # The first field, "name", is a simple property. It will be retrieved from
+ # the value "name" in the remote definition for a system, identifyed by the
# +:owner+ argument.
- #
- # The second field, "owners", is similarly retrieved from a property also
- # named "owners" in the remote definition. However, this property is a
- # collection: in this case, it is an array of definitions itself. The
- # +:type+ argument identifies what the +local+ class type is that will be
+ #
+ # The second field, "owners", is similarly retrieved from a property also
+ # named "owners" in the remote definition. However, this property is a
+ # collection: in this case, it is an array of definitions itself. The
+ # +:type+ argument identifies what the +local+ class type is that will be
# used to represent each element in the collection.
- #
+ #
# A +cobbler_collection+ is packed in one of two ways: either as an array
# of values or as a hash of keys and associated values. These are defined by
# the +:packing+ argument with the values +Array+ and +Hash+, respectively.
- #
+ #
# The +cobbler_lifecycle+ method allows for declaring different methods for
# retrieving remote instances of the class. These methods are:
- #
+ #
# +find_one+ - the remote method to find a single instance,
# +find_all+ - the remote method to find all instances,
# +remove+ - the remote method to remote an instance
- #
+ #
class Base
-
- @@hostname = nil
+
+ @@hostname = nil
@@connection = nil
@@auth_token = nil
-
- @definitions = nil
-
- def initialize(definitions)
- @definitions = definitions
+
+ attr_accessor :definitions
+
+ def initialize(defs = nil)
+ @definitions = defs ? defs : Hash.new
end
-
+
# Sets the connection. This method is only needed during unit testing.
#
def self.connection=(connection)
@@connection = connection
end
-
+
# Returns or creates a new connection.
#
def self.connect(writable)
@@connection || XMLRPC::Client.new2("http://#{@@hostname}/cobbler_api#{writable ? '_rw' : ''}")
end
-
+
# Establishes a connection with the Cobbler system.
#
def self.begin_transaction(writable = false)
@@connection = connect(writable)
end
-
+
# Sets the username.
#
def self.username=(username)
@@username = username
end
-
+
# Sets the password.
#
def self.password=(password)
@@password = password
end
-
+
# Logs into the Cobbler server.
#
def self.login
(@@auth_token || make_call('login', @@username, @@password))
end
-
+
# Makes a remote call.
#
def self.make_call(*args)
raise Exception.new('No connection established.') unless @@connection
-
+
@@connection.call(*args)
end
-
+
# Ends a transaction and disconnects.
#
def self.end_transaction
@@connection = nil
@@auth_token = nil
end
-
- def definition(key)
- @definitions ? @definitions[key] : nil
- end
-
- def store_definition(key,value)
- @definitions[key] = value
- end
-
- def definitions
- @definitions
- end
-
+
def self.hostname=(hostname)
@@hostname = hostname
end
-
+
class << self
# Creates a complete finder method
- #
+ #
def cobbler_lifecycle(*args)
methods = args.first
methods.keys.each do |key|
-
+
method = methods[key]
-
+
case key
when :find_all then
module_eval <<-"end;"
@@ -188,7 +176,7 @@ module Cobbler
return nil
end
end;
-
+
when :remove then
module_eval <<-"end;"
def self.remove(name)
@@ -203,24 +191,21 @@ module Cobbler
result
end
end;
-
+
end
end
end
-
+
# Allows for dynamically declaring fields that will come from
# Cobbler.
#
def cobbler_field(field,*args) # :nodoc:
-
- defined = false
-
if args
for arg in args
for key in arg.keys
- case key
- when :findable then
-
+ case key
+ when :findable then
+
module_eval <<-"end;"
def self.find_by_#{field.to_s}(value,&block)
properties = make_call('#{arg[key]}',value)
@@ -230,30 +215,23 @@ module Cobbler
return nil
end
end;
-
- end
- end
- end
- end
-
- module_eval <<-"end;"
- def #{field.to_s}(&block)
- return definition('#{field.to_s}')
- end
- def #{field.to_s}=(value)
- store_definition('#{field.to_s}',value)
+ end
end
- end;
+ end
+ end
+
+ module_eval("def #{field}() @definitions['#{field.to_s}']; end")
+ module_eval("def #{field}=(val) @definitions['#{field.to_s}'] = val; end")
end
-
+
# Allows a field to be defined as a collection of objects. The type for that
# other class must be provided.
#
def cobbler_collection(field, *args) # :nodoc:
- classname = 'String'
+ classname = 'String'
packing = 'Array'
-
+
# process collection definition
args.each do |arg|
classname = arg[:type] if arg[:type]
@@ -264,20 +242,20 @@ module Cobbler
end
end
end
-
+
module_eval <<-"end;"
def #{field.to_s}(&block)
unless @#{field.to_s}
@#{field.to_s} = #{packing}.new
- values = definition('#{field.to_s}')
-
+ values = @definitions['#{field.to_s}']
+
case "#{packing}"
when "Array" then
values.each do |value|
@#{field.to_s} << #{classname}.new(value)
- end
+ end
when "Hash" then
values.keys.each do |key|
@@ -294,8 +272,8 @@ module Cobbler
@#{field.to_s} = replacement
end
end;
-
+
end
end
- end
+ end
end
diff --git a/contrib/ruby/lib/cobbler/distro.rb b/contrib/ruby/lib/cobbler/distro.rb
index b4c4fd0b..a8e85b93 100644
--- a/contrib/ruby/lib/cobbler/distro.rb
+++ b/contrib/ruby/lib/cobbler/distro.rb
@@ -41,7 +41,7 @@ module Cobbler
cobbler_field :parent
cobbler_field :ks_meta
- def initialize(definitions)
+ def initialize(definitions = nil)
super(definitions)
end
diff --git a/contrib/ruby/lib/cobbler/image.rb b/contrib/ruby/lib/cobbler/image.rb
index c5a84f77..21b5c356 100644
--- a/contrib/ruby/lib/cobbler/image.rb
+++ b/contrib/ruby/lib/cobbler/image.rb
@@ -42,7 +42,7 @@ module Cobbler
cobbler_field :virt_cpus
cobbler_field :parent
- def initialize(definitions)
+ def initialize(definitions = nil)
super(definitions)
end
diff --git a/contrib/ruby/lib/cobbler/network_interface.rb b/contrib/ruby/lib/cobbler/network_interface.rb
index 3e25f2a2..1de6dc14 100644
--- a/contrib/ruby/lib/cobbler/network_interface.rb
+++ b/contrib/ruby/lib/cobbler/network_interface.rb
@@ -32,7 +32,7 @@ module Cobbler
cobbler_field :virt_bridge
cobbler_field :ip_address
- def initialize(args)
+ def initialize(args = nil)
@definitions = args
end
diff --git a/contrib/ruby/lib/cobbler/profile.rb b/contrib/ruby/lib/cobbler/profile.rb
index 6a7b9d4c..9ee27df1 100644
--- a/contrib/ruby/lib/cobbler/profile.rb
+++ b/contrib/ruby/lib/cobbler/profile.rb
@@ -49,7 +49,7 @@ module Cobbler
cobbler_field :ks_meta
cobbler_field :kickstart
- def initialize(definitions)
+ def initialize(definitions = nil)
super(definitions)
end
diff --git a/contrib/ruby/lib/cobbler/system.rb b/contrib/ruby/lib/cobbler/system.rb
index c01196cf..2322bc7c 100644
--- a/contrib/ruby/lib/cobbler/system.rb
+++ b/contrib/ruby/lib/cobbler/system.rb
@@ -33,6 +33,7 @@ module Cobbler
cobbler_field :name
cobbler_field :parent
cobbler_field :profile
+ cobbler_field :image
cobbler_field :depth
cobbler_collection :kernel_options, :packing => :hash
cobbler_field :kickstart
@@ -48,7 +49,7 @@ module Cobbler
cobbler_field :virt_type
cobbler_field :virt_bridge
- def initialize(definitions)
+ def initialize(definitions = nil)
super(definitions)
end
@@ -63,8 +64,9 @@ module Cobbler
sysid = Base.make_call('new_system',token)
- Base.make_call('modify_system',sysid,'name',self.name,token)
- Base.make_call('modify_system',sysid,'profile',profile,token)
+ Base.make_call('modify_system',sysid,'name', name, token)
+ Base.make_call('modify_system',sysid,'profile',profile,token) if profile
+ Base.make_call('modify_system',sysid,'image', image, token) if image
if @interfaces
count = 0
diff --git a/contrib/ruby/test/test_system.rb b/contrib/ruby/test/test_system.rb
index dae87321..82c3935a 100644
--- a/contrib/ruby/test/test_system.rb
+++ b/contrib/ruby/test/test_system.rb
@@ -41,8 +41,9 @@ module Cobbler
@auth_token = 'OICU812B4'
@system_id = 717
- @new_system = 'system1'
- @profile = 'profile1'
+ @system_name = 'system1'
+ @profile_name = 'profile1'
+ @image_name = 'image1'
@nics = Array.new
@nic_details = {'mac_address' => '00:11:22:33:44:55:66:77'}
@nic = NetworkInterface.new(@nic_details)
@@ -118,14 +119,14 @@ module Cobbler
@connection.should_receive(:call).with('login',@username,@password).once.returns(@auth_token)
@connection.should_receive(:call).with('update').once.returns{ false }
- system = System.new(:name => @system_name, :profile => @profile_name)
+ system = System.new('name' => @system_name, 'profile' => @profile_name)
assert_raise(Exception) {system.save}
end
- # Ensures that saving a system works as expected.
+ # Ensures that saving a system based on a profile works as expected.
#
- def test_save
+ def test_save_with_profile
@connection.should_receive(:call).with('login',@username,@password).once.returns(@auth_token)
@connection.should_receive(:call).with('update').once.returns { true }
@connection.should_receive(:call).with('new_system',@auth_token).once.returns(@system_id)
@@ -133,7 +134,22 @@ module Cobbler
@connection.should_receive(:call).with('modify_system',@system_id,'profile',@profile_name,@auth_token).once.returns(true)
@connection.should_receive(:call).with('save_system',@system_id,@auth_token).once.returns(true)
- system = System.new(:name => @system_name, :profile => @profile_name)
+ system = System.new('name' => @system_name, 'profile' => @profile_name)
+
+ system.save
+ end
+
+ # Ensures that saving a system based on an image works as expected.
+ #
+ def test_save_with_image
+ @connection.should_receive(:call).with('login',@username,@password).once.returns(@auth_token)
+ @connection.should_receive(:call).with('update').once.returns { true }
+ @connection.should_receive(:call).with('new_system',@auth_token).once.returns(@system_id)
+ @connection.should_receive(:call).with('modify_system',@system_id,'name',@system_name,@auth_token).once.returns(true)
+ @connection.should_receive(:call).with('modify_system',@system_id,'image',@image_name,@auth_token).once.returns(true)
+ @connection.should_receive(:call).with('save_system',@system_id,@auth_token).once.returns(true)
+
+ system = System.new('name' => @system_name, 'image' => @image_name)
system.save
end
@@ -151,7 +167,7 @@ module Cobbler
@nic.bundle_for_saving(0),@auth_token).once.returns(true)
@connection.should_receive(:call).with('save_system',@system_id,@auth_token).once.returns(true)
- system = System.new(:name => @system_name, :profile => @profile_name)
+ system = System.new('name' => @system_name, 'profile' => @profile_name)
system.interfaces = @nics
system.save