From cc0021f55c70ecd7289bc169c8fb67f5fdefed21 Mon Sep 17 00:00:00 2001
From: Ashay Humane <ashay.humane@gmail.com>
Date: Sat, 1 May 2010 21:04:30 -0700
Subject: [PATCH] Feature #179 with Generic Hosts edit page.

---
 app/controllers/hosts_controller.rb       |   96 ++++++++++++++++++++++++++++-
 app/views/hosts/_minilist.html.erb        |   56 ++++++++++-------
 app/views/hosts/add_parameter.html.erb    |   14 ++++
 app/views/hosts/edit_action.html.erb      |   20 ++++++
 app/views/hosts/edit_multiple.html.erb    |   21 ++++++
 app/views/hosts/select_hostgroup.html.erb |   18 ++++++
 config/routes.rb                          |    4 +-
 public/javascripts/host_checkbox.js       |   40 ++++++++++++
 8 files changed, 243 insertions(+), 26 deletions(-)
 create mode 100644 app/views/hosts/add_parameter.html.erb
 create mode 100644 app/views/hosts/edit_action.html.erb
 create mode 100644 app/views/hosts/edit_multiple.html.erb
 create mode 100644 app/views/hosts/select_hostgroup.html.erb
 create mode 100644 public/javascripts/host_checkbox.js

diff --git a/app/controllers/hosts_controller.rb b/app/controllers/hosts_controller.rb
index c646997..64e2091 100644
--- a/app/controllers/hosts_controller.rb
+++ b/app/controllers/hosts_controller.rb
@@ -47,6 +47,15 @@ class HostsController < ApplicationController
     end
   end
 
+  def edit_action
+    if session[:selected].nil?
+      flash[:foreman_error] = 'No Hosts selected'
+      redirect_to(hosts_path)
+    else
+      @hosts = Host.find(session[:selected].keys)
+    end
+  end
+
   def edit
     @host = Host.find(params[:id])
     @environment = @host.environment
@@ -64,6 +73,85 @@ class HostsController < ApplicationController
     end
   end
 
+  def edit_multiple
+    if session[:selected].nil?
+      flash[:foreman_error] = 'No Hosts selected'
+      redirect_to(hosts_path)
+    else
+      @hosts = Host.find(session[:selected].keys)
+    end
+  end
+
+  def update_multiple
+    if params[:reset] == "true"
+      reset_session
+      @search = Host.search(params[:search])
+      @hosts = @search.all.paginate(:page => params[:page])
+      flash[:foreman_notice] = 'Session cleared.'
+      redirect_to(hosts_path) and return
+    end
+    @hosts_without_params ||= {}
+    @hosts_to_edit = Host.find(session[:selected].keys)
+    @hosts_to_edit.each do |host_to_edit|
+      myparams = []
+      host_to_edit.host_parameters.each do |hp|
+        myparams << hp.name.to_str
+        unless params[:name][hp.name].chomp.empty?
+           hp.value = params[:name][hp.name]
+           host_to_edit.save(perform_validation = false)
+        end
+      end
+      params[:name].each do |pname,pvalue|
+        if !myparams.include?(pname) && !pvalue.chomp.empty?
+          @hosts_without_params[host_to_edit.name] ||= []
+          @hosts_without_params[host_to_edit.name] << pname
+        end
+      end
+    end
+    if @hosts_without_params.length !=0
+        reset_session
+        render :text => "\#These hosts did not have the selected parameters and were not updated: <br></br>" + @hosts_without_params.to_yaml.gsub("\n","<br>")
+    else
+    reset_session
+    flash[:foreman_notice] = 'Updated hosts!'
+    redirect_to(hosts_path)
+    end
+  end
+
+  def add_parameter
+    if session[:selected].nil?
+      flash[:foreman_error] = 'No Hosts selected'
+      redirect_to(hosts_path)
+    else
+      @hosts = Host.find(session[:selected].keys)
+    end
+  end
+
+  def select_hostgroup
+    if session[:selected].nil?
+      flash[:foreman_error] = 'No Hosts selected'
+      redirect_to(hosts_path)
+    else
+      @hosts = Host.find(session[:selected].keys, :order => "hostgroup_id ASC")
+    end
+  end
+
+  def update_hostgroup
+    if params["hostgroup"]["hostgroup_id_equals"].empty?
+      flash[:foreman_error] = 'No Hostgroup selected!'
+      redirect_to(select_hostgroup_hosts_path) and return
+    end
+    @hosts_to_edit = Host.find(:all, :conditions => {:id => session[:selected].keys})
+    @hosts_to_edit.each do |host_to_edit|
+      hg = Hostgroup.find(params["hostgroup"]["hostgroup_id_equals"])
+      !hg.nil? && host_to_edit.hostgroup=hg
+      host_to_edit.save(perform_validation = false)
+    end
+    reset_session
+    flash[:foreman_notice] = 'Updated hosts: Changed Hostgroup'
+    redirect_to(hosts_path)
+  end
+
   def destroy
     @host = Host.find(params[:id])
     if @host.destroy
@@ -92,6 +180,13 @@ class HostsController < ApplicationController
     assign_parameter "operatingsystem"
   end
 
+  def save_checkbox
+    session[:selected] ||= {}
+    params[:is_checked] == "true" && session[:selected][params[:box]] = params[:box]
+    params[:is_checked] == "false" && session[:selected][params[:box]] = nil
+    render :nothing => true
+  end
+
  # list AJAX methods
   def fact_selected
     @fact_name_id = params[:search_fact_values_fact_name_id_eq].to_i
@@ -232,5 +327,4 @@ class HostsController < ApplicationController
       return head(:not_found)
     end
   end
-
 end
diff --git a/app/views/hosts/_minilist.html.erb b/app/views/hosts/_minilist.html.erb
index 12ca4b3..40fedce 100644
--- a/app/views/hosts/_minilist.html.erb
+++ b/app/views/hosts/_minilist.html.erb
@@ -1,3 +1,4 @@
+<%= javascript_include_tag "host_checkbox" %>
 <div id="hostlist">
 <%= link_to_function "Search", toggle_div(:search) %>
 
@@ -16,31 +17,38 @@
 </div>
 
   <% if hosts.size > 0 -%>
-    <table class="list">
-      <caption> <%= header ||= "" -%> </caption>
-      <tr>
-        <th><%= order @search, :by => :name %></th>
-        <th>Operating system</th>
-        <th>Environment</th>
-        <th>Model</th>
-        <th>Host Group</th>
-        <th><%= order @search, :by => :last_report %></th>
-        <th>Edit</th>
-        <th>Delete</th>
-      </tr>
-      <% hosts.each do |host| -%>
-        <tr class="<%= cycle("even", "odd") -%>">
-          <td><%=name_column(host) %></td>
-          <td><%=h host.try(:os) %></td>
-          <td><%=h host.try(:environment) %></td>
-          <td><%=h host.try(:model) %></td>
-          <td><%=h host.try(:hostgroup) %></td>
-          <td><%=last_report_column(host) %></td>
-          <td><%= link_to  'Edit', edit_host_url(host)  %></td>
-          <td><%= link_to "Destroy", host, :confirm => 'Are you sure?', :method => :delete %></td>
+    <br><input type='button' value='Toggle Check All' onClick='toggleCheck()' />
+    <% form_tag(edit_action_hosts_path,:method => "get", :id => "host_select_form") do %>
+    <%= submit_tag "Edit Checked Hosts" %>
+      <table class="list">
+        <caption> <%= header ||= "" -%> </caption>
+        <tr>
+          <th></th>
+          <th><%= order @search, :by => :name %></th>
+          <th>Operating system</th>
+          <th>Environment</th>
+          <th>Model</th>
+          <th>Host Group</th>
+          <th><%= order @search, :by => :last_report %></th>
+          <th>Edit</th>
+          <th>Delete</th>
+        </tr>
+        <% hosts.each do |host| -%>
+          <tr class="<%= cycle("even", "odd") -%>">
+            <td><%= check_box_tag "host_ids[]", host.id, false, :class => 'host_select_boxes', :onClick => 'insertHostVal(this)' %></td>
+            <td><%=name_column(host) %></td>
+            <td><%=h host.try(:os) %></td>
+            <td><%=h host.try(:environment) %></td>
+            <td><%=h host.try(:model) %></td>
+            <td><%=h host.try(:hostgroup) %></td>
+            <td><%=last_report_column(host) %></td>
+            <td><%= link_to  'Edit', edit_host_url(host)  %></td>
+            <td><%= link_to "Destroy", host, :confirm => 'Are you sure?', :method => :delete %></td>
+          </tr>
         <% end -%>
-      </tr>
-    </table>
+      </table>
+    <%= submit_tag "Edit Checked Hosts" %>
+    <% end %>
   <% else -%>
     <p>No Hosts found</p>
   <% end -%>
diff --git a/app/views/hosts/add_parameter.html.erb b/app/views/hosts/add_parameter.html.erb
new file mode 100644
index 0000000..738d140
--- /dev/null
+++ b/app/views/hosts/add_parameter.html.erb
@@ -0,0 +1,14 @@
+<h3>Add/Remove Parameters Coming soon... </h3>
+
+<h4>Click this button to clear all selected hosts and return to Hosts list:</h5>
+<%= button_to 'Clear Selected Hosts', :controller => 'hosts', :action => 'update_multiple', :reset => "true" %>
+<h5>Please check the following list of hosts whose parameters will be changed:</h4>
+<br>
+<ul>
+  <% for host in @hosts %>
+    <li>
+      <%= hidden_field_tag "host_ids[]", host.id %>
+      <%= host.name %>
+    </li>
+  <% end %>
+</ul>
diff --git a/app/views/hosts/edit_action.html.erb b/app/views/hosts/edit_action.html.erb
new file mode 100644
index 0000000..1a346eb
--- /dev/null
+++ b/app/views/hosts/edit_action.html.erb
@@ -0,0 +1,20 @@
+<h2>Choose the action you want to apply to the selected Hosts:</h2>
+
+<%= button_to 'Change Group', :controller => 'hosts', :action => 'select_hostgroup' %>
+<br>
+<%= button_to 'Edit Parameters', :controller => 'hosts', :action => 'edit_multiple' %>
+<br>
+<%= button_to 'Add/Remove Parameters', :controller => 'hosts', :action => 'add_parameter' %>
+
+<h4>Click this button to clear all selected hosts and return to Hosts list:</h5>
+<%= button_to 'Clear Selected Hosts', :controller => 'hosts', :action => 'update_multiple', :reset => "true" %>
+<h5>Please check the following list of hosts which will be edited:</h4>
+<br>
+<ul>
+  <% for host in @hosts %>
+    <li>
+      <%= hidden_field_tag "host_ids[]", host.id %>
+      <%=h host.name %>
+    </li>
+  <% end %>
+</ul>
diff --git a/app/views/hosts/edit_multiple.html.erb b/app/views/hosts/edit_multiple.html.erb
new file mode 100644
index 0000000..556d697
--- /dev/null
+++ b/app/views/hosts/edit_multiple.html.erb
@@ -0,0 +1,21 @@
+<% form_tag update_multiple_hosts_path, :method => :post do %>
+  <% for param in Parameter.find(:all, :select => "DISTINCT name") %>
+    <div>
+      <%= text_field :name, param.name, :size=>'150' %>
+      <%= param.name %>
+    </div>
+  <% end %>
+ <p><%= submit_tag "Edit these Parameter(s)" %></p>
+<% end %>
+
+<h4>Please check the following list of hosts whose parameters will be changed:</h4>
+<h5>Click this button to clear all selected hosts and return to Hosts list:</h5>
+<%= button_to 'Clear Selected Hosts', :controller => 'hosts', :action => 'update_multiple', :reset => "true" %>
+<ul>
+  <% for host in @hosts %>
+    <li>
+      <%= hidden_field_tag "host_ids[]", host.id %>
+      <%= host.name %>
+    </li>
+  <% end %>
+</ul>
diff --git a/app/views/hosts/select_hostgroup.html.erb b/app/views/hosts/select_hostgroup.html.erb
new file mode 100644
index 0000000..bb26947
--- /dev/null
+++ b/app/views/hosts/select_hostgroup.html.erb
@@ -0,0 +1,18 @@
+<% form_for :hostgroup, :url => { :action => "update_hostgroup" },:html => { :method => :post } do |f| %>
+  <%= f.label :hostgroup, "Select Hostgroup:<br>" %>
+  <%= f.collection_select :hostgroup_id_equals, Hostgroup.all, :id, :name, :include_blank => true %>
+  <p><%= f.submit "Change Hostgroup!" %></p>
+<% end %>
+
+<h4>Click this button to clear all selected hosts and return to Hosts list:</h5>
+<%= button_to 'Clear Selected Hosts', :controller => 'hosts', :action => 'update_multiple', :reset => "true" %>
+<h5>Please check the following list of hosts whose Hostgroup will be changed:</h4>
+<ul>
+  <% for host in @hosts %>
+    <li>
+      <%= hidden_field_tag "host_ids[]", host.id %>
+      <%= host.try(:hostgroup) %>
+      <%= host.try(:name) %>
+    </li>
+  <% end %>
+</ul>
diff --git a/config/routes.rb b/config/routes.rb
index 364d6ba..18881dc 100644
--- a/config/routes.rb
+++ b/config/routes.rb
@@ -8,7 +8,9 @@ ActionController::Routing::Routes.draw do |map|
                 :member => {:report => :get, :reports => :get, :facts => :get,
                   :environment_selected => :post, :architecture_selected => :post, :os_selected => :post,
                   :storeconfig_klasses => :get, :externalNodes => :get, :setBuild => :get, :puppetrun => :get},
-                :collection => { :show_search => :get}
+                  :collection => { :show_search => :get, :edit_action => :get, :edit_multiple => :get,
+                  :update_multiple => :post, :save_checkbox => :get, :add_parameter => :get, :select_hostgroup => :get,
+                  :update_hostgroup => :post}
   map.dashboard '/dashboard', :controller => 'dashboard'
   map.audit '/audit', :controller => 'audit'
   map.statistics '/statistics', :controller => 'statistics'
diff --git a/public/javascripts/host_checkbox.js b/public/javascripts/host_checkbox.js
new file mode 100644
index 0000000..9734a41
--- /dev/null
+++ b/public/javascripts/host_checkbox.js
@@ -0,0 +1,40 @@
+function toggleCheck() {
+  $$('#host_select_form input.host_select_boxes').each(function(box){
+                                                                box.checked=!box.checked;
+                                                                //if (box.checked == true ) { box.checked = false; }
+                                                                //if (box.checked == false) { box.checked = true;  }
+                                                                insertHostVal(box);
+                                                                });
+  return false;
+}
+function insertHostVal(cbox) {
+  //alert(cbox.value)
+  //if (cbox.checked){
+  //    alert(cbox.value)
+  //hosts
+  var request = new Ajax.Request('hosts/save_checkbox', {
+                method: 'get',
+                parameters: { box: cbox.value, is_checked: cbox.checked },
+                onSuccess: function(res){
+                   return false;
+                },
+                onFailure: function(res){
+                   alert("Something failed! Select the checkbox again.")
+                   return false;
+                }
+              });
+}
+
+function clearSession() {
+  var request = new Ajax.Request('update_multiple', {
+                method: 'post',
+                parameters: { resetSession: "true" },
+                onSuccess: function(res){
+                   return false;
+                },
+                onFailure: function(res){
+                   alert("Something failed! Click the button again.")
+                   return false;
+                }
+              });
+}
-- 
1.6.3.3

