foreman_chef 0.0.4 → 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 9116ff8cbc2d9611bc315667f4da6a871fc4ee70
4
- data.tar.gz: 5fd304dd80a76a7b0c469ae1ba8bc4df3c8e9b38
3
+ metadata.gz: 48b50dcd6355797ece89dee99d3f9ebef0d347e4
4
+ data.tar.gz: 79ae27dc6b1c7d23b6d7d2acc942b3f6a94aea2a
5
5
  SHA512:
6
- metadata.gz: 6a511666f44ada17e426fb497c578b879c0de51e98192ad19bd20a01fa2235e6df7662a18da95e6c9f327e078b1aeec1ede5bfbcadd8319b8ae2e38ffabbfacf
7
- data.tar.gz: 98a678f999e673e98b05a8b8684767b266187f3d5fd69d5e28513ab2170fedb6bfd9504e74c144089648d958062cbaf8559912c8d8364aea9f8d6132d6e80d7e
6
+ metadata.gz: 894eca488c8631c39043510f530404c0f3cc1ea6bee1854cd41b7d0a214ac5d04fc08754390727b23cc01aa27b539625a45be881946a12b969b431ad953ad1f7
7
+ data.tar.gz: 3d2920bec28fe08a6c7bbb39ee6e61a779c35d31cdf4c0f9e740515fb940a674ae055491b65aeb5441b6af8ead9990b969f69c0213b29b05b3cfaee02d548aec
data/README.md CHANGED
@@ -1,17 +1,17 @@
1
1
  # ForemanChef
2
2
 
3
- This plugin adds a Chef fact improter to Foreman. It basically means that when you setup your chef
3
+ This plugin adds a Chef fact importer to Foreman. It basically means that when you setup your chef
4
4
  clients to use foreman handlers (https://github.com/theforeman/chef-handler-foreman) and install
5
5
  this plugin you receive nested facts from chef-client.
6
6
 
7
7
  This plugin expects foreman to support nested facts which is was added in 1.4.
8
- To install this plugin you just have to add this line to your gemfile
8
+ To install this plugin you just have to add this line to your Gemfile.
9
9
 
10
10
  ```ruby
11
- gem 'foreman_chef', :git => 'https://github.com/ares/foreman_chef'
11
+ gem 'foreman_chef'
12
12
  ```
13
13
 
14
- and run bundle install. Don't forget to restart foreman after this change.
14
+ and run ```bundle install```. Don't forget to restart foreman after this change.
15
15
 
16
16
  If you want to use this in production I recommend to combine this plugin with foreman-background
17
17
  (https://github.com/ohadlevy/foreman-background) which runs report and facts import as a background
@@ -19,4 +19,10 @@ tasks.
19
19
 
20
20
  ## License
21
21
 
22
- This project rocks and uses MIT-LICENSE.
22
+ Copyright (c) 2013-2014 Marek Hulán
23
+
24
+ This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
25
+
26
+ This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
27
+
28
+ You should have received a copy of the GNU General Public License along with this program. If not, see http://www.gnu.org/licenses/.
@@ -0,0 +1,14 @@
1
+ module ForemanChef
2
+ module ChefProxyForm
3
+ def chef_proxy_form(f)
4
+ # Don't show this if we have no Chef proxies, otherwise always include blank
5
+ # so the user can choose not to use puppet on this host
6
+ proxies = SmartProxy.with_taxonomy_scope_override(@location,@organization).with_features('Chef')
7
+ return if proxies.count == 0
8
+ select_f f, :chef_proxy_id, proxies, :id, :name,
9
+ { :include_blank => blank_or_inherit_f(f, :chef_proxy) },
10
+ { :label => _("Chef proxy"),
11
+ :help_inline => _("Use this foreman proxy as an entry point to your Chef, node will be managed via this proxy") }
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,33 @@
1
+ module Actions
2
+ module ForemanChef
3
+ module Client
4
+ class Destroy < Actions::EntryAction
5
+
6
+ def plan(fqdn, proxy)
7
+ if ::Setting::ForemanChef.auto_deletion
8
+ client_exists_in_chef = proxy.show_client(fqdn)
9
+ if client_exists_in_chef
10
+ plan_self :chef_proxy_id => proxy.id, :fqdn => fqdn
11
+ end
12
+ end
13
+ end
14
+
15
+ def run
16
+ proxy = ::SmartProxy.find_by_id(input[:chef_proxy_id])
17
+ action_logger.debug "Deleting client #{input[:fqdn]} on proxy #{proxy.name} at #{proxy.url}"
18
+ self.output = proxy.delete_client(input[:fqdn])
19
+ end
20
+
21
+ def humanized_name
22
+ _("Delete client")
23
+ end
24
+
25
+ def humanized_input
26
+ input[:fqdn]
27
+ end
28
+
29
+ end
30
+ end
31
+ end
32
+ end
33
+
@@ -0,0 +1,43 @@
1
+ module Actions
2
+ module ForemanChef
3
+ module Host
4
+ class Destroy < Actions::EntryAction
5
+
6
+ def plan(host)
7
+ action_subject(host)
8
+ if (::Setting::ForemanChef.auto_deletion && proxy = ::SmartProxy.find_by_id(host.chef_proxy_id))
9
+ node_exists_in_chef = proxy.show_node(host.name)
10
+ if node_exists_in_chef
11
+ plan_self :chef_proxy_id => host.chef_proxy_id
12
+ end
13
+
14
+ plan_action Actions::ForemanChef::Client::Destroy, host.name, proxy
15
+ end
16
+ end
17
+
18
+ def run
19
+ proxy = ::SmartProxy.find_by_id(input[:chef_proxy_id])
20
+ action_logger.debug "Deleting #{input[:host][:name]} on proxy #{proxy.name} at #{proxy.url}"
21
+ self.output = proxy.delete_node(input[:host][:name])
22
+ end
23
+
24
+ def humanized_name
25
+ _("Delete host")
26
+ end
27
+
28
+ def humanized_input
29
+ input[:host] && input[:host][:name]
30
+ end
31
+
32
+ def cli_example
33
+ return unless input[:host]
34
+ <<-EXAMPLE
35
+ hammer host delete --id '#{task_input[:host][:id]}'
36
+ EXAMPLE
37
+ end
38
+
39
+ end
40
+ end
41
+ end
42
+ end
43
+
@@ -0,0 +1,53 @@
1
+ module ProxyAPI
2
+ module ForemanChef
3
+ class ChefProxy
4
+ PREFIX = 'chef'
5
+
6
+ class Node < ProxyAPI::Resource
7
+ def initialize(args)
8
+ @url = "#{args[:url]}/#{PREFIX}/nodes"
9
+ super args
10
+ end
11
+ end
12
+
13
+ class Client < ProxyAPI::Resource
14
+ def initialize(args)
15
+ @url = "#{args[:url]}/#{PREFIX}/clients"
16
+ super args
17
+ end
18
+ end
19
+
20
+ def initialize(args)
21
+ @args = args
22
+ end
23
+
24
+ # Shows a Chef Node entry
25
+ # [+key+] : String containing the hostname
26
+ # Returns : Hash representation of host on chef server
27
+ def show_node(key)
28
+ Node.new(@args).send(:get, key)
29
+ end
30
+
31
+ # Deletes a Chef Node entry
32
+ # [+key+] : String containing the hostname
33
+ # Returns : Boolean status
34
+ def delete_node(key)
35
+ Node.new(@args).send(:delete, key)
36
+ end
37
+
38
+ # Shows a Chef Client entry
39
+ # [+key+] : String containing the hostname
40
+ # Returns : Hash representation of host on chef server
41
+ def show_client(key)
42
+ Client.new(@args).send(:get, key)
43
+ end
44
+
45
+ # Deletes a Chef Client entry
46
+ # [+key+] : String containing the hostname
47
+ # Returns : Boolean status
48
+ def delete_client(key)
49
+ Client.new(@args).send(:delete, key)
50
+ end
51
+ end
52
+ end
53
+ end
@@ -0,0 +1,10 @@
1
+ module ForemanChef
2
+ module ChefProxyAssociation
3
+ extend ActiveSupport::Concern
4
+
5
+ included do
6
+ belongs_to :chef_proxy, :class_name => "SmartProxy"
7
+ end
8
+
9
+ end
10
+ end
@@ -0,0 +1,19 @@
1
+ module ForemanChef
2
+ module Concerns
3
+ module HostActionSubject
4
+ extend ActiveSupport::Concern
5
+ include ForemanTasks::Concerns::ActionSubject
6
+ include ForemanTasks::Concerns::ActionTriggering
7
+
8
+ def destroy_action
9
+ sync_action!
10
+ ::Actions::ForemanChef::Host::Destroy
11
+ end
12
+
13
+ def action_input_key
14
+ "host"
15
+ end
16
+
17
+ end
18
+ end
19
+ end
@@ -4,6 +4,10 @@ module ForemanChef
4
4
  ForemanChef::FactName
5
5
  end
6
6
 
7
+ def self.authorized_smart_proxy_features
8
+ 'Chef'
9
+ end
10
+
7
11
  def self.support_background
8
12
  true
9
13
  end
@@ -0,0 +1,16 @@
1
+ module ForemanChef
2
+ module HostExtensions
3
+ extend ActiveSupport::Concern
4
+
5
+ included do
6
+ alias_method_chain :set_hostgroup_defaults, :chef_proxy
7
+ end
8
+
9
+ def set_hostgroup_defaults_with_chef_proxy
10
+ set_hostgroup_defaults_without_chef_proxy
11
+ return unless hostgroup
12
+ assign_hostgroup_attributes(['chef_proxy_id'])
13
+ end
14
+
15
+ end
16
+ end
@@ -0,0 +1,18 @@
1
+ module ForemanChef
2
+ module HostgroupExtensions
3
+ extend ActiveSupport::Concern
4
+
5
+ def inherited_chef_proxy_id
6
+ read_attribute(:chef_proxy_id) || nested(:chef_proxy_id)
7
+ end
8
+
9
+ def chef_proxy
10
+ if ancestry.present?
11
+ SmartProxy.with_features('Chef').find_by_id(inherited_chef_proxy_id)
12
+ else
13
+ super
14
+ end
15
+ end
16
+
17
+ end
18
+ end
@@ -0,0 +1,38 @@
1
+ module ForemanChef
2
+ module SmartProxyExtensions
3
+ extend ActiveSupport::Concern
4
+
5
+ # create or overwrite instance methods...
6
+ def show_node(fqdn)
7
+ reply = ProxyAPI::ForemanChef::ChefProxy.new(:url => url).show_node(fqdn)
8
+ JSON.parse(reply)
9
+ rescue RestClient::ResourceNotFound
10
+ logger.debug "Node '#{fqdn}' not found"
11
+ return false
12
+ end
13
+
14
+ def delete_node(fqdn)
15
+ begin
16
+ reply = ProxyAPI::ForemanChef::ChefProxy.new(:url => url).delete_node(fqdn)
17
+ JSON.parse(reply)
18
+ #rescue RestClient::
19
+ end
20
+ end
21
+
22
+ def show_client(fqdn)
23
+ reply = ProxyAPI::ForemanChef::ChefProxy.new(:url => url).show_client(fqdn)
24
+ JSON.parse(reply)
25
+ rescue RestClient::ResourceNotFound
26
+ logger.debug "Client '#{fqdn}' not found"
27
+ return false
28
+ end
29
+
30
+ def delete_client(fqdn)
31
+ begin
32
+ reply = ProxyAPI::ForemanChef::ChefProxy.new(:url => url).delete_client(fqdn)
33
+ JSON.parse(reply)
34
+ #rescue RestClient::
35
+ end
36
+ end
37
+ end
38
+ end
@@ -0,0 +1,17 @@
1
+ class Setting::ForemanChef < Setting
2
+
3
+ def self.load_defaults
4
+ # Check the table exists
5
+ return unless super
6
+
7
+ self.transaction do
8
+ [
9
+ self.set('auto_deletion', N_("Enable the auto deletion of mapped objects in chef-server through foreman-proxy (currently node and client upon host deletion)"), true),
10
+ ].each { |s| self.create! s.update(:category => "Setting::ForemanChef")}
11
+ end
12
+
13
+ true
14
+
15
+ end
16
+
17
+ end
@@ -0,0 +1,16 @@
1
+ Deface::Override.new(:virtual_path => "hosts/_form",
2
+ :name => "add_chef_proxy",
3
+ :insert_bottom => "div#primary",
4
+ :text => ("<%= chef_proxy_form(f) %>")
5
+ )
6
+
7
+ Deface::Override.new(:virtual_path => "hostgroups/_form",
8
+ :name => "add_chef_proxy",
9
+ :insert_bottom => "div#primary",
10
+ :text => ("<%= chef_proxy_form(f) %>")
11
+ )
12
+
13
+ # strings used above, for the purposes of extraction only, as they're not
14
+ # detected within the full override template string above
15
+ N_('Chef proxy')
16
+ N_('Use this foreman proxy as an entry point to your Chef, node will be managed via this proxy')
@@ -0,0 +1,5 @@
1
+ class AddChefProxyIdToHost < ActiveRecord::Migration
2
+ def change
3
+ add_column :hosts, :chef_proxy_id, :integer
4
+ end
5
+ end
@@ -0,0 +1,5 @@
1
+ class AddChefProxyIdToHostgroup < ActiveRecord::Migration
2
+ def change
3
+ add_column :hostgroups, :chef_proxy_id, :integer
4
+ end
5
+ end
data/db/seeds.rb ADDED
@@ -0,0 +1 @@
1
+ Feature.find_or_create_by_name('Chef')
@@ -1,25 +1,51 @@
1
+ require 'deface'
2
+
1
3
  module ForemanChef
2
4
  #Inherit from the Rails module of the parent app (Foreman), not the plugin.
3
5
  #Thus, inhereits from ::Rails::Engine and not from Rails::Engine
4
6
  class Engine < ::Rails::Engine
5
7
 
8
+ rake_tasks do
9
+ Rake::Task['db:seed'].enhance do
10
+ ForemanChef::Engine.load_seed
11
+ end
12
+ end
13
+
14
+ initializer 'foreman_chef.load_default_settings', :before => :load_config_initializers do
15
+ require_dependency File.expand_path('../../../app/models/setting/foreman_chef.rb', __FILE__) if (Setting.table_exists? rescue(false))
16
+ end
17
+
6
18
  initializer "foreman_chef.load_app_instance_data" do |app|
7
19
  app.config.paths['db/migrate'] += ForemanChef::Engine.paths['db/migrate'].existent
8
20
  end
9
21
 
10
- initializer 'foreman_chef.register_plugin', :after=> :finisher_hook do |app|
22
+ initializer "foreman_chef.register_paths" do |app|
23
+ ForemanTasks.dynflow.config.eager_load_paths.concat(%W[#{ForemanChef::Engine.root}/app/lib/actions])
24
+ end
25
+
26
+ initializer 'foreman_chef.register_plugin', :after => :finisher_hook do |app|
11
27
  Foreman::Plugin.register :foreman_chef do
12
28
  requires_foreman '>= 1.4'
13
- end if Foreman::Plugin rescue(false)
29
+ end
14
30
  end
15
31
 
16
- #initializer 'foreman_chef.helper' do |app|
17
- # ActionView::Base.send :include, FactValuesHelper
18
- #end
32
+ initializer 'foreman_chef.chef_proxy_form' do |app|
33
+ ActionView::Base.send :include, ChefProxyForm
34
+ end
35
+
36
+ initializer 'foreman_chef.dynflow_world' do |app|
37
+ ForemanTasks.dynflow.require!
38
+ end
19
39
 
20
- #Include extenstions to models in this config.to_prepare block
40
+ #Include extensions to models in this config.to_prepare block
21
41
  config.to_prepare do
42
+ ::Host::Managed.send :include, ForemanChef::HostExtensions
43
+ ::Hostgroup.send :include, ForemanChef::HostgroupExtensions
44
+ ::Host::Managed.send :include, ChefProxyAssociation
45
+ ::Hostgroup.send :include, ChefProxyAssociation
46
+ ::SmartProxy.send :include, SmartProxyExtensions
22
47
  ::FactImporter.register_fact_importer(:foreman_chef, ForemanChef::FactImporter)
48
+ ::Host::Base.send :include, ForemanChef::Concerns::HostActionSubject
23
49
  end
24
50
  end
25
51
  end
@@ -1,3 +1,3 @@
1
1
  module ForemanChef
2
- VERSION = "0.0.4"
2
+ VERSION = "0.1.0"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: foreman_chef
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.4
4
+ version: 0.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Marek Hulan
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-01-22 00:00:00.000000000 Z
11
+ date: 2015-01-14 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails
@@ -24,6 +24,34 @@ dependencies:
24
24
  - - ~>
25
25
  - !ruby/object:Gem::Version
26
26
  version: 3.2.8
27
+ - !ruby/object:Gem::Dependency
28
+ name: deface
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - '>='
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - '>='
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: foreman-tasks
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ~>
46
+ - !ruby/object:Gem::Version
47
+ version: 0.6.9
48
+ type: :runtime
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ~>
53
+ - !ruby/object:Gem::Version
54
+ version: 0.6.9
27
55
  - !ruby/object:Gem::Dependency
28
56
  name: sqlite3
29
57
  requirement: !ruby/object:Gem::Requirement
@@ -45,9 +73,23 @@ executables: []
45
73
  extensions: []
46
74
  extra_rdoc_files: []
47
75
  files:
76
+ - app/overrides/add_chef_proxy.rb
77
+ - app/helpers/foreman_chef/chef_proxy_form.rb
48
78
  - app/models/foreman_chef/fact_name.rb
79
+ - app/models/foreman_chef/smart_proxy_extensions.rb
80
+ - app/models/foreman_chef/chef_proxy_association.rb
81
+ - app/models/foreman_chef/hostgroup_extensions.rb
82
+ - app/models/foreman_chef/host_extensions.rb
49
83
  - app/models/foreman_chef/fact_importer.rb
84
+ - app/models/foreman_chef/concerns/host_action_subject.rb
85
+ - app/models/setting/foreman_chef.rb
86
+ - app/lib/actions/foreman_chef/client/destroy.rb
87
+ - app/lib/actions/foreman_chef/host/destroy.rb
88
+ - app/lib/proxy_api/foreman_chef/chef_proxy.rb
50
89
  - config/routes.rb
90
+ - db/migrate/20140513144804_add_chef_proxy_id_to_hostgroup.rb
91
+ - db/migrate/20140220145827_add_chef_proxy_id_to_host.rb
92
+ - db/seeds.rb
51
93
  - lib/foreman_chef/engine.rb
52
94
  - lib/foreman_chef/version.rb
53
95
  - lib/foreman_chef.rb
@@ -67,7 +109,6 @@ files:
67
109
  - test/dummy/public/404.html
68
110
  - test/dummy/public/500.html
69
111
  - test/dummy/public/422.html
70
- - test/dummy/log/development.log
71
112
  - test/dummy/config/database.yml
72
113
  - test/dummy/config/environment.rb
73
114
  - test/dummy/config/locales/en.yml
@@ -124,7 +165,6 @@ test_files:
124
165
  - test/dummy/public/404.html
125
166
  - test/dummy/public/500.html
126
167
  - test/dummy/public/422.html
127
- - test/dummy/log/development.log
128
168
  - test/dummy/config/database.yml
129
169
  - test/dummy/config/environment.rb
130
170
  - test/dummy/config/locales/en.yml
@@ -1,4 +0,0 @@
1
- Connecting to database specified by database.yml
2
- Connecting to database specified by database.yml
3
- Connecting to database specified by database.yml
4
- Connecting to database specified by database.yml