Skip to content

Commit

Permalink
wip
Browse files Browse the repository at this point in the history
  • Loading branch information
Paul Kelly committed Oct 6, 2010
1 parent 251af69 commit c4b4755
Show file tree
Hide file tree
Showing 7 changed files with 253 additions and 118 deletions.
83 changes: 83 additions & 0 deletions app/helpers/application_helper.rb
Original file line number Diff line number Diff line change
@@ -1,4 +1,87 @@
# Methods added to this helper will be available to all templates in the application.
module ApplicationHelper

def graph(type,opts = {})
Gchart.send(type, {:size => '400x150', :bg => "E6DFCF", :format => "image_tag"}.merge(opts))
end

def show_habtm associations
render :partial => 'common/show_habtm', :collection => associations, :as => :association
end

def edit_habtm klass, association
render :partial => 'common/edit_habtm', :locals =>{ :klass => klass, :associations => association.all.delete_if{|e| e == klass}}
end

def link_to_remove_fields(name, f)
f.hidden_field(:_destroy) + link_to_function(image_tag("false.png", :title => "remove"), "remove_fields(this)")
end

def link_to_add_fields(name, f, association, partial = nil)
new_object = f.object.class.reflect_on_association(association).klass.new
fields = f.fields_for(association, new_object, :child_index => "new_#{association}") do |builder|
render((partial.nil? ? association.to_s.singularize + "_fields" : partial), :f => builder)
end
link_to_function(name, h("add_fields(this, \"#{association}\", \"#{escape_javascript(fields)}\")"))
end

def toggle_div div
update_page do |page|
page << "if ($('#{div}').visible()) {"
page[div].visual_effect :BlindUp
page << "} else {"
page[div].visual_effect :BlindDown
page << "}"
end
end

def link_to_remove_puppetclass klass
link_to_function image_tag("delete.png") + " " + klass.name do |page|
page["selected_puppetclass_#{klass.id}"].remove
#TODO if the class is already selected, removing it will not add it to the avail class list
page << "if ($('puppetclass_#{klass.id}')) {"
page["puppetclass_#{klass.id}"].show
page << "}"
end
end

def link_to_add_puppetclass klass, type
# link to remote is faster than inline js when having many classes
link_to_remote "&nbsp;&nbsp;&nbsp;" + image_tag("add.png") + " " + klass.klass,
:url => assign_puppetclass_path(klass, :type => type),
:position => {:after => {:success => "selected_classes" }}
end

def searchtab title, search, options
opts = {:action => params[:action], :tab_name => title, :search => search}
selected_class = options[:selected] ? "selectedtab" : ""
content_tag(:li) do
link_to opts, :class => selected_class do
title + (options[:no_close_button] ? "": (link_to "x", opts.merge(:remove_me => true), :class => "#{selected_class} close"))
end
end
end

def toggle_searchbar
update_page do |page|
page['search'].toggle
page['tabs'].toggle
end
end

# a simple helper to load the google JS only on pages which requires it
def gcharts_script
content_for :head do
"<script src=http://www.google.com/jsapi></script>"
end
end

def fact_name_select
param = params[:search]["#{@via}fact_name_id_eq"] if params[:search]
return param.to_i unless param.empty?
return @fact_name_id if @fact_name_id
end

def settings_dropdown
choices = [
['Additional Settings', ""],
Expand Down
2 changes: 2 additions & 0 deletions init.rb
Original file line number Diff line number Diff line change
@@ -1 +1,3 @@
#require_dependency File.join(File.dirname(__FILE__), "..", "..", "..", "config", "initializers", "foreman")
require 'netdb_manager'
ActiveSupport::Dependencies.load_once_paths.delete lib_path
11 changes: 4 additions & 7 deletions lib/netdb_manager.rb
Original file line number Diff line number Diff line change
@@ -1,13 +1,10 @@
ActiveSupport::Dependencies.load_once_paths.delete File.dirname(__FILE__)
# Patch the host with a transactional update facility that we use to hook our update code
require 'netdb_manager/host_ext'
require 'netdb_manager/active_record_ext'

# Rails Engines works against us in some ways as it ensures that the last loaded module overrides the first.
# As the application's version of application_helper.rb is loaded last it overrides our overrides.
# Never mind, just load our overrides again, as the last loaded module. Maybe I should drop engines. . . .
require_or_load File.join(File.dirname(__FILE__), '..',"app", "helpers", "application_helper.rb")
ActionController::Base.prepend_view_path(File.join(File.dirname(__FILE__), '..', 'app', 'views'))

#HostsController.prepend_view_path(File.join(File.dirname(__FILE__), '..', 'app', 'views'))
# Our code overrides the application code
Engines.disable_application_code_loading = true

# If we define a view then this is the one we should use.
Engines.disable_application_view_loading = true
20 changes: 20 additions & 0 deletions lib/netdb_manager/active_record_ext.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
module NetdbManager
module ActiveRecordExtensions
def self.included(base) #:nodoc:
base.send :include, InstanceMethods
base.class_eval { alias_method_chain :before_save, :netdb_support }
end

module InstanceMethods
def before_save_with_netdb_support
if self.class.to_s == "Host"
require_dependency 'netdb_manager/host_ext'
elsif self.class.to_s == "User"
require_dependency 'netdb_manager/user_ext'
end
before_save_without_netdb_support
end
end
end
end
ActiveRecord::Callbacks.send :include, NetdbManager::ActiveRecordExtensions
204 changes: 105 additions & 99 deletions lib/netdb_manager/host_ext.rb
Original file line number Diff line number Diff line change
@@ -1,112 +1,118 @@
module NetdbManager
def self.included(base)
# This implementation requires memcache
if [Rails.configuration.cache_store].flatten[0] == :mem_cache_store
require 'dhcp'
require 'iscdhcp'
require 'ipaddr'
include DHCP
else
message = "*********************************************************************\n" +
"DHCP and DNS management require that you install the memcache service\n" +
"and that you add this line to environment.db \n" +
"config.cache_store = :mem_cache_store \n" +
"and edit config.initializers/session_store to set = :mem_cache_store \n" +
"*********************************************************************\n"
RAILS_DEFAULT_LOGGER.warn message
puts message
exit
end

base.extend ClassMethods
base.send :include, InstanceMethods
end

module InstanceMethods
def save_network_data
return true if RAILS_ENV == "test"
if @dhcp
dhcpServer = @dhcp.serverFor subnet.number
if new_record?
setDHCP dhcpServer
end
module HostExtensions
def self.included(base)
# This implementation requires memcache
if [Rails.configuration.cache_store].flatten[0] == :mem_cache_store
require_dependency 'dhcp'
require_dependency 'iscdhcp'
require_dependency 'ipaddr'
include DHCP
else
true # No netdb management unless we use memcache
message = "*********************************************************************\n" +
"DHCP and DNS management require that you install the memcache service\n" +
"and that you add this line to environment.db \n" +
"config.cache_store = :mem_cache_store \n" +
"and edit config.initializers/session_store to set = :mem_cache_store \n" +
"*********************************************************************\n"
RAILS_DEFAULT_LOGGER.warn message
puts message
exit
end

base.extend ClassMethods
base.send :include, InstanceMethods
base.send :after_save, :transactional_update
true
end
def delDHCP dhcpServer
status = log_status("Delete a DHCP reservation for #{name}/#{ip}", dhcpServer){
dhcpServer.delReservation self
}
return status unless sp_valid?
log_status("Delete a DHCP reservation for #{sp_name}/#{sp_ip}", dhcpServer){
dhcpServer.delReservation self, true
}
end
# Updates the DHCP scope to add a reservation for this host
# [+dhcpServer+] : A DHCPServer object
# +returns+ : Boolean true on success
def setDHCP dhcpServer
status = log_status("Add a DHCP reservation for #{name}/#{ip}", dhcpServer){
dhcpServer.setReservation self
}
return status unless sp_valid?
log_status("Add a DHCP reservation for #{sp_name}/#{sp_ip}", dhcpServer){
dhcpServer.setReservation self, true
}
end

def log_status message, server, &block
if server
logger.info "#{message}"
unless result = yield(block)
first, rest = message.match(/(\w*)(.*)/)[1,2]
message = "Failed to " + first.downcase + rest + ": #{server.message}"
errors.add_to_base server.message
logger.error message

module InstanceMethods
#after_save :transactional_update
def save_network_data
return true if RAILS_ENV == "test"
if @dhcp
dhcpServer = @dhcp.serverFor subnet.number
if new_record?
setDHCP dhcpServer
end
else
true # No netdb management unless we use memcache
end
result
else
errors.add_to_base("Access denied")
false
end
end

def transactional_update
begin
initialise_network_cache
save_network_data
def delDHCP dhcpServer
status = log_status("Delete a DHCP reservation for #{name}/#{ip}", dhcpServer){
dhcpServer.delReservation self
}
return status unless sp_valid?
log_status("Delete a DHCP reservation for #{sp_name}/#{sp_ip}", dhcpServer){
dhcpServer.delReservation self, true
}
end
# Updates the DHCP scope to add a reservation for this host
# [+dhcpServer+] : A DHCPServer object
# +returns+ : Boolean true on success
def setDHCP dhcpServer
status = log_status("Add a DHCP reservation for #{name}/#{ip}", dhcpServer){
dhcpServer.setReservation self
}
return status unless sp_valid?
log_status("Add a DHCP reservation for #{sp_name}/#{sp_ip}", dhcpServer){
dhcpServer.setReservation self, true
}
end

def log_status message, server, &block
if server
logger.info "#{message}"
unless result = yield(block)
first, rest = message.match(/(\w*)(.*)/)[1,2]
message = "Failed to " + first.downcase + rest + ": #{server.message}"
errors.add_to_base server.message
logger.error message
end
result
else
errors.add_to_base("Access denied")
false
end
end

def initialise_network_cache
return true unless @user
return true if SETTINGS[:unattended] and SETTINGS[:unattended] == false

@dhcp = Rails.cache.fetch(:dhcp, :expires_in => NET_TTL){
DHCP::Dhcp.new(session)
}.dup # For some reason the object is frozen in this implementation of the cache!
raise RuntimeException, "Unable to create DHCP memcache storage" unless @dhcp

# The DHCP instance needs access to the session as some of its DHCPServer implementations need to know about the user
per_user_dhcp_data = session[:dhcp_data] ||= {:user => @user.login}
@dhcp.personalise(per_user_dhcp_data)
true
rescue => e
errors.add_to_base "Failed to update the network databases"
raise ActiveRecord::Rollback + e.message
false
end

def transactional_update
puts "performing transactional update"
Rails.logger.debug "performing transactional update"
begin
initialise_network_cache
save_network_data
true
rescue
errors.add_to_base "Failed to update the network databases"
raise
false
end
end
end
end

module ClassMethods
def initialise_network_cache
return true unless @user
return true if SETTINGS[:unattended] and SETTINGS[:unattended] == false

@dhcp = Rails.cache.fetch(:dhcp, :expires_in => NET_TTL){
DHCP::Dhcp.new(session)
}.dup # For some reason the object is frozen in this implementation of the cache!
raise RuntimeException, "Unable to create DHCP memcache storage" unless @dhcp

# The DHCP instance needs access to the session as some of its DHCPServer implementations need to know about the user
per_user_dhcp_data = session[:dhcp_data] ||= {:user => @user.login}
@dhcp.personalise(per_user_dhcp_data)
true
end

def reload_network_data
Rails.cache.clear
head :created

module ClassMethods
def reload_network_data
Rails.cache.clear
head :created
end
end
end
end

# And yes we need to put this in ActiveRecord and NOT Host
ActiveRecord::Base.send :include, NetdbManager
Host.send :include, NetdbManager::HostExtensions
12 changes: 0 additions & 12 deletions lib/netdb_manager/routing.rb

This file was deleted.

Loading

0 comments on commit c4b4755

Please sign in to comment.