cupper 0.1.3 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: f3c9044f099f9507069454620cf7aae32285dcd3
4
- data.tar.gz: 99a8cf640b7a66eb12f235aa95e8997f61f47f8a
3
+ metadata.gz: db74b52ddda16fe1e73d2e89e891452ef7bada67
4
+ data.tar.gz: 725d29c9e8aa93842a26d0e0ee0b67f325e9fa7b
5
5
  SHA512:
6
- metadata.gz: bfb771781dee62c1c911a9fca95675345a1d29b53f4066a5dc7f95a92b8636ff652ed6704186ec29ae49bb46d506b04cd53f455ae2cb33dd9bf3d67ee4c90657
7
- data.tar.gz: ae7534f3f2018676e5a22c161463d364319b17a7808ef00e33917d466ebaf107e50ea864bddc1e0006caaee20a85cd3e74db1c189ed0e76a8e3a9f0a61bf9ea3
6
+ metadata.gz: 919f337af1d06ab30b6ddcecb6bcd75dccf96e2863d12766795e79a0139bf5659773b18e1f4b2a36fe256f398770ad2fcbfbd37db4840d6e5e44789501a6dbc0
7
+ data.tar.gz: 29a8b4dc77e18b0bb74afd76c3751de73f377b67040c6dc534e3495087344ddd3074cde6b9ba570bc5f1bf8a186c2d36ef465d999e569a74e46390aed67329af
data/README.md CHANGED
@@ -1,8 +1,27 @@
1
1
  # Cupper
2
2
 
3
- [![Join the chat at https://gitter.im/cupper-reverse-recipe/cupper](https://badges.gitter.im/cupper-reverse-recipe/cupper.svg)](https://gitter.im/cupper-reverse-recipe/cupper?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
3
+ [![Join the chat at https://gitter.im/cupper-reverse-recipe/cupper](https://badges.gitter.im/cupper-reverse-recipe/cupper.svg)](https://gitter.im/cupper-reverse-recipe/cupper?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
4
4
  [![Coverage Status](https://coveralls.io/repos/github/cupper-reverse-recipe/cupper/badge.svg?branch=master)](https://coveralls.io/github/cupper-reverse-recipe/cupper?branch=master)
5
5
 
6
+ Taste your environment and creates a cookbook for it!
7
+ Cupper is a command line tool that runs in some environment (see supoorted
8
+ platforms below) and creates a cookbook based on it. It will collect
9
+ information about the package installed, file configuration, groups, users,
10
+ links, links and services. Once you have this cookbook, you can change
11
+ according to your needs, or just runs it in another environment.
12
+
13
+ ## Support Platform
14
+
15
+ Currently, Cupper support the platforms listed below. It means that we
16
+ tested on this specific platforms and versions, but may work on others
17
+ version. Let us know :)
18
+
19
+ | Debian | Arch |
20
+ | :----------: | :-------------: |
21
+ | Jessie 8.6 | (Coming soon) |
22
+ | Jessie 8.2 | . |
23
+
24
+
6
25
  ## Installation
7
26
 
8
27
  Add this line to your application's Gemfile:
@@ -15,16 +34,70 @@ And then execute:
15
34
 
16
35
  $ bundle
17
36
 
18
- Or install it yourself as:
37
+ Or install it yourself with:
19
38
 
20
39
  $ gem install cupper
21
40
 
22
41
  ## Usage
23
42
 
43
+ Cupper is a command line tool. All commands are available through bash/shell
44
+ terminal.
45
+ First create a Cupper project with the following command:
46
+
47
+ ```
48
+ $ cupper create <project_name>
49
+ ```
50
+
51
+ This will create a directory within a given name. The structure of the
52
+ Cupper project contains:
53
+
54
+ ```
55
+ .project
56
+ |
57
+ |- cookbooks/
58
+ |- Cupperfile
59
+ |- .sensibles
60
+ ```
61
+ - **cookbook**: the recipe that are generated is stored in this directory
62
+ - **Cupperfile**: configuration file that allows you to customize some items
63
+ inside the cookbook
64
+ - **.sensibles**: specifies all files that are not suppose to be collected
65
+ (patten witha a regex is given)
66
+
67
+ Inside the project directory you can run the command:
68
+ ```
69
+ $ cupper generate
70
+ ```
71
+ This will generate a cookbook based on the configurations on the machine
72
+ and store in `cookbooks/` directory.
73
+
24
74
 
25
75
  ## Development
26
76
 
77
+ This is a common gem, so doesn't needs a bunch of configuration on your
78
+ environment to develop something. Just use a ruby environment with rbenv
79
+ or RVM (ruby 2.2.0 or higher).
80
+
81
+ ### Ohai
82
+
83
+ We use [Ohai](https://github.com/chef/ohai) gem to extract the information
84
+ about the environment. We created our Ohai plugins, it's code made in ruby,
85
+ so nothing unusual. Check the official
86
+ [doc](https://docs.chef.io/ohai.html) of Ohai for more knowledge about it.
27
87
 
28
88
  ## Contributing
29
89
 
90
+ Any contribution are welcome :)
91
+ Steps:
92
+ - Make a fork
93
+ - Clone the repository
94
+ - Bundle!
95
+ - Make a change
96
+ - Send a Pull Request
97
+
98
+ ## Found any bug? Open a issue
30
99
 
100
+ Just go to the
101
+ [issue](https://github.com/cupper-reverse-recipe/cupper/issues) page and
102
+ report the problem. Use a lablel to make it easier to identify if it's
103
+ a bug or a suggestion.
@@ -25,4 +25,6 @@ Gem::Specification.new do |spec|
25
25
 
26
26
  spec.add_runtime_dependency 'thor', '~> 0.19.1'
27
27
  spec.add_runtime_dependency 'ohai', '~> 8.15', '>= 8.15.1'
28
+ spec.add_runtime_dependency 'colorize', '0.8.1'
29
+ spec.add_runtime_dependency 'i18n', '0.7.0'
28
30
  end
@@ -5,13 +5,19 @@ require 'cupper/ohai_plugins'
5
5
  require 'cupper/collect'
6
6
  require 'cupper/cookbook'
7
7
  require 'cupper/entity'
8
+ require 'cupper/config/config'
9
+ require 'cupper/cupperfile'
10
+ require 'cupper/environment'
11
+ require 'cupper/errors'
12
+
8
13
 
9
14
 
10
15
  module Cupper
11
- CUPPER_ROOT = File.expand_path(File.dirname(__FILE__))
12
- OHAI_PLUGINS_PATH = CUPPER_ROOT + '/cupper/plugins/ohai'
16
+ CUPPER_ROOT = File.expand_path(File.dirname(__FILE__))
17
+ OHAI_PLUGINS_PATH = CUPPER_ROOT + '/cupper/plugins/ohai'
13
18
  CUPPER_PLUGINS_PATH = CUPPER_ROOT + '/cupper/plugins/cupper'
14
- TEMPLATE_PATH = CUPPER_ROOT + '/cupper/templates'
19
+ TEMPLATE_PATH = CUPPER_ROOT + '/cupper/templates'
20
+ ENVIRONMENT = Environment.new
15
21
 
16
22
  # REVIEW: maybe there is a better way and place to load all plugins
17
23
  # Loading all cupper plugins
@@ -7,6 +7,7 @@ require 'thor'
7
7
  require 'cupper/project'
8
8
  require 'cupper/cookbook'
9
9
  require 'cupper/ohai_plugins'
10
+ require 'cupper/environment'
10
11
 
11
12
  module Cupper
12
13
  class Cli < Thor
@@ -30,7 +31,12 @@ module Cupper
30
31
  desc 'generate', 'Extract configuration and create a cookbook'
31
32
  method_option :verbose, :aliases => '-v', :desc => 'Enable output log'
32
33
  def generate
33
- puts "Generating the Cookbook"
34
+ puts "Generating the Cookbook..."
35
+
36
+ puts "Setting up the environment"
37
+ Cupper::ENVIRONMENT.check_env(Errors::NoEnvironmentError, Cupper::ENVIRONMENT.root_path)
38
+ Cupper::ENVIRONMENT.cupperfile
39
+
34
40
  cookbook = Cookbook.new
35
41
  if options.verbose?
36
42
  puts "Verbose mode enabled"
@@ -0,0 +1,60 @@
1
+ require "pathname"
2
+ require "cupper/errors"
3
+ require 'colorize'
4
+
5
+
6
+ module Cupper
7
+ module Config
8
+ extend self
9
+
10
+ def parameter(*names)
11
+ names.each do |name|
12
+ attr_accessor name
13
+
14
+ # For each given symbol we generate accessor method that sets option's
15
+ # value being called with an argument, or returns option's current value
16
+ # when called without arguments
17
+ define_method name do |*values|
18
+ value = values.first
19
+ value ? self.send("#{name}=", value) : instance_variable_get("@#{name}")
20
+ end
21
+ end
22
+ end
23
+
24
+ def self.configure
25
+ self.config do
26
+ parameter :native_configured
27
+ parameter :sensible_files
28
+ parameter :allow_downgrade
29
+ parameter :sourceless_packages
30
+ parameter :package_version
31
+
32
+ native_configured true
33
+ end
34
+ # TODO: raise stuff if mandatory stuff is not defined in cupperfile
35
+ end
36
+
37
+ def config(&block)
38
+ instance_eval &block
39
+ end
40
+
41
+ def load(cupperfile)
42
+ Kernel.load cupperfile
43
+ result = Cupper::Config
44
+
45
+ puts "Configuration loaded successfully, finalizing and returning"
46
+ return result
47
+ end
48
+
49
+ def self.all_sensibles
50
+ sensibles = Array.new
51
+ unless sensible_files
52
+ env = Cupper::ENVIRONMENT
53
+ File.open("#{env.root_path}/.sensibles").each do |line|
54
+ sensibles.push line.chomp unless line.strip.chomp.match /^#.*/ or line.chomp.empty?
55
+ end
56
+ end
57
+ sensibles
58
+ end
59
+ end
60
+ end
@@ -6,7 +6,7 @@ module Cupper
6
6
  class Cookbook
7
7
  # TODO: Read config file to tell the project path and configs
8
8
  def initialize(cookbookname='default')
9
- @cookbook_path = "#{Dir.getwd}/#{cookbookname}"
9
+ @cookbook_path = "#{Dir.getwd}/cookbooks/#{cookbookname}"
10
10
  @cookbook_files_path = "#{@cookbook_path}/files"
11
11
  @cookbook_recipes_path = "#{@cookbook_path}/recipes"
12
12
  @recipe_deps = [ # TODO this is hard code to reflect all_recipes. Refactor this later
@@ -1,22 +1,44 @@
1
1
  module Cupper
2
2
  class Cupperfile
3
3
 
4
- def initialize(loader, keys)
5
- @keys = keys
6
- @loader = loader
7
- @config, _ = loader.load(keys)
4
+ def initialize(key)
5
+ @key = key
6
+ @config, _ = Cupper::Config.load(key)
8
7
  end
9
8
 
10
- protected
9
+ def machine_being_read(name, env)
10
+ # Load the configuration for the machine
11
+ results = cupper_config(name, env)
12
+ config = results[:config]
11
13
 
12
- def find_cupperfile(search_path)
13
- ["Cupperfile", "cupperfile"].each do |cupperfile|
14
- current_path = search_path.join(cupperfile)
15
- return current_path if current_path.file?
16
- end
14
+ # Create the machine and cache it for future calls. This will also
15
+ # return the machine from this method.
16
+ return new_machine(name, config, env)
17
+ end
17
18
 
18
- nil
19
+ def new_machine(name, config, env)
20
+ machine = Attribute.new
21
+ class << machine
22
+ attr_accessor :name
23
+ attr_accessor :config
24
+ attr_accessor :env
25
+ end
26
+ machine.name = name
27
+ machine.config = config
28
+ machine.env = env
29
+ machine
19
30
  end
20
31
 
32
+ def cupper_config(name, env)
33
+ cupperfile = env.find_cupperfile(env.root_path)
34
+ if cupperfile
35
+ config = Cupper::Config.load(cupperfile)
36
+ end
37
+
38
+ return {
39
+ config: config,
40
+ # TODO: add other meaningfull returns
41
+ }
42
+ end
21
43
  end
22
44
  end
@@ -35,7 +35,7 @@ module Cupper
35
35
  end
36
36
 
37
37
  def render_template
38
- ERB.new(@template).result(binding)
38
+ ERB.new(@template, 0, '-').result(binding)
39
39
  end
40
40
 
41
41
  # Treats entity as a file or as a dir
@@ -1,7 +1,8 @@
1
+ require 'colorize'
1
2
  require "pathname"
2
3
  require "cupper/cupperfile"
3
4
  require "cupper/version"
4
- require 'colorize'
5
+ require "cupper/errors"
5
6
 
6
7
  module Cupper
7
8
  class Environment
@@ -33,6 +34,7 @@ module Cupper
33
34
  raise ex if !root_path
34
35
  rescue ex => ex
35
36
  puts "#{ex.message}".red
37
+ exit
36
38
  end
37
39
  end
38
40
 
@@ -101,20 +103,6 @@ module Cupper
101
103
  "#<#{self.class}: #{@cwd}>".encode('external')
102
104
  end
103
105
 
104
- def config_loader
105
- return @config_loader if @config_loader
106
-
107
- root_cupperfile = nil
108
- if root_path
109
- root_cupperfile = find_cupperfile(root_path, @cupperfile_name)
110
- end
111
-
112
- @config_loader = Config::Loader.new(
113
- Config::VERSIONS, Config::VERSIONS_ORDER)
114
- @config_loader.set(:root, root_cupperfile) if root_cupperfile
115
- @config_loader
116
- end
117
-
118
106
  def environment(cupperfile, **opts)
119
107
  path = File.expand_path(cupperfile, root_path)
120
108
  file = File.basename(path)
@@ -160,11 +148,11 @@ module Cupper
160
148
  end
161
149
 
162
150
  def cupperfile
163
- @cupperfile ||= cupperfile.new(config_loader, [:home, :root])
151
+ @cupperfile ||= Cupper::Cupperfile.new(find_cupperfile(@root_path))
164
152
  end
165
153
 
166
154
  def find_cupperfile(search_path, filenames=nil)
167
- filenames ||= ["cupperfile", "cupperfile"]
155
+ filenames ||= ["Cupperfile", "cupperfile"]
168
156
  filenames.each do |cupperfile|
169
157
  current_path = search_path.join(cupperfile)
170
158
  return current_path if current_path.file?
@@ -75,10 +75,18 @@ module Cupper
75
75
  error_key(:no_env)
76
76
  end
77
77
 
78
+ class CupperfileSyntaxError < CupperError
79
+ error_key(:cupperfile_syntax_error)
80
+ end
81
+
78
82
  class LocalDataDirectoryNotAccessible < CupperError
79
83
  error_key(:local_data_dir_not_accessible)
80
84
  end
81
85
 
86
+ class CupperfileLoadError < CupperError
87
+ error_key(:cupperfile_load_error)
88
+ end
89
+
82
90
  end
83
91
 
84
92
  end
@@ -22,7 +22,12 @@ module Cupper
22
22
  'cookbooks'
23
23
  ]
24
24
  @files = [
25
- 'CupperFile'
25
+ 'Cupperfile',
26
+ ]
27
+ # TODO: this should not be separated from the others
28
+ # files. Try to get them together.
29
+ @hidden = [
30
+ 'sensibles'
26
31
  ]
27
32
  end
28
33
 
@@ -35,6 +40,10 @@ module Cupper
35
40
  Structure.new(dir, "#{@dir}/#{@name}", nil, Entity::DIR).create
36
41
  Structure.new(file, "#{@dir}/#{@name}", file).create
37
42
  end
43
+
44
+ @hidden.each do |file|
45
+ Structure.new(".#{file}", "#{@dir}/#{@name}", file).create
46
+ end
38
47
  end
39
48
  end
40
49
  end
@@ -34,10 +34,6 @@ module Cupper
34
34
  (file[1]['type'].split.first(2).join(' ').match('symbolic link'))
35
35
  end
36
36
 
37
- def dir_type?(file)
38
- file[1]['type'].match('directory')
39
- end
40
-
41
37
  def text_type?(file)
42
38
  file[1]['type'].match('text') or file[1]['type'].match('ASCII')
43
39
  end
@@ -144,7 +140,7 @@ module Cupper
144
140
  def expand_files(files)
145
141
  att = Array.new
146
142
  files.each do |attr|
147
- if text_type?(attr) and (!(attr[1]['related'].nil?) or attr[0].include? "/etc/apt/sources.list")
143
+ if valid_cookbook_file?(attr)
148
144
  path = attr[0]
149
145
  source = attr[0]
150
146
  group = attr[1]['group']
@@ -162,6 +158,17 @@ module Cupper
162
158
  att
163
159
  end
164
160
 
161
+ def valid_cookbook_file?(attr)
162
+ (text_type?(attr) and
163
+ !sensible_files?(attr) and
164
+ (!(attr[1]['related'].nil?) or
165
+ attr[0].include? "/etc/apt/sources.list"))
166
+ end
167
+
168
+ def sensible_files?(attr)
169
+ !!(Config.all_sensibles.find { |file| attr[0].match Regexp.new("^#{file}$") })
170
+ end
171
+
165
172
  # Every attribute object is created dynamic
166
173
  def new_package(name, version)
167
174
  package = Attribute.new
@@ -0,0 +1,43 @@
1
+ # # -*- mode: ruby -*-
2
+ # # # vi: set ft=ruby :
3
+ #
4
+ # The Cupperfile defines rules to be follow when the
5
+ # recipe is being generated.
6
+ #
7
+
8
+ Cupper::Config.config do
9
+ Cupper::Config.configure
10
+
11
+ # The files considered sensible are the ones with
12
+ # critical information on it. For example, a file
13
+ # that has a pem key or a certificate, can`t be
14
+ # treaded as a normal file.
15
+ # Specify the files, or extensions in the '.sensibles'
16
+ # on the root of the Cupper project.
17
+ #
18
+ # Set this variable to true if you want to ignore
19
+ # the .sensibles and copy all the files to the cookbook
20
+ sensible_files false
21
+
22
+ # The packages extracted from the target environment may
23
+ # have a older version. If you want to create a recipe
24
+ # that allows a downgrade flag to the package manager,
25
+ # set this variable to true
26
+ allow_downgrade false
27
+
28
+ # Some packages on the environment may not have a source
29
+ # repository related to. This packages will not appear
30
+ # in the cookbook, because the package was installed
31
+ # using other methods other than the default.
32
+ #
33
+ # Setting this variable to true will extract the packages
34
+ # without a source repository. Please check the repositories
35
+ # on the machine that the cookbook will run before running
36
+ # the cookbook.
37
+ sourceless_packages false
38
+
39
+ # The packages are extracted with the version instaled in the
40
+ # machine. You may want to not specify the version on the
41
+ # recipe. If so, set the variable to false.
42
+ package_version true
43
+ end
@@ -5,6 +5,7 @@
5
5
  #
6
6
  <% for @cb in @sources_list %>
7
7
  cookbook_file '<%= @cb.path %>' do
8
+ source '<%= @cb.source %>'
8
9
  owner '<%= @cb.owner %>'
9
10
  group '<%= @cb.group %>'
10
11
  mode '<%= @cb.mode %>'
@@ -13,7 +14,9 @@ end
13
14
 
14
15
  <% for @package in @packages %>
15
16
  package '<%= @package.name %>' do
17
+ <% if Cupper::Config.package_version -%>
16
18
  version '<%= @package.version %>'
19
+ <% end -%>
17
20
  action :install
18
21
  end
19
22
  <% end %>
@@ -0,0 +1,5 @@
1
+ # List all the files that you want to ignore when
2
+ # extracting
3
+ *.pem
4
+ *.crt
5
+
@@ -1,3 +1,3 @@
1
1
  module Cupper
2
- VERSION = '0.1.3'.freeze
2
+ VERSION = '0.2.0'.freeze
3
3
  end
@@ -15,3 +15,10 @@ en:
15
15
  state is not accessible. The directory specified as the local data
16
16
  directory must be both readable and writable for the user that is
17
17
  running cupper.
18
+ cupperfile_syntax_error: |-
19
+ There is a syntax error in the following cupperfile. The syntax error
20
+ message is reproduced below for convenience.
21
+ cupperfile_load_error: |-
22
+ There was an error loading a Cupperfile. The file being loaded
23
+ and the error message are shown below. This is usually caused by
24
+ a syntax error.
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: cupper
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.3
4
+ version: 0.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Paulo Tada
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2016-12-23 00:00:00.000000000 Z
12
+ date: 2017-01-02 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: bundler
@@ -87,6 +87,34 @@ dependencies:
87
87
  - - ">="
88
88
  - !ruby/object:Gem::Version
89
89
  version: 8.15.1
90
+ - !ruby/object:Gem::Dependency
91
+ name: colorize
92
+ requirement: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - '='
95
+ - !ruby/object:Gem::Version
96
+ version: 0.8.1
97
+ type: :runtime
98
+ prerelease: false
99
+ version_requirements: !ruby/object:Gem::Requirement
100
+ requirements:
101
+ - - '='
102
+ - !ruby/object:Gem::Version
103
+ version: 0.8.1
104
+ - !ruby/object:Gem::Dependency
105
+ name: i18n
106
+ requirement: !ruby/object:Gem::Requirement
107
+ requirements:
108
+ - - '='
109
+ - !ruby/object:Gem::Version
110
+ version: 0.7.0
111
+ type: :runtime
112
+ prerelease: false
113
+ version_requirements: !ruby/object:Gem::Requirement
114
+ requirements:
115
+ - - '='
116
+ - !ruby/object:Gem::Version
117
+ version: 0.7.0
90
118
  description: Taste your system and create a recipe
91
119
  email:
92
120
  - paulohtfs@gmail.com
@@ -108,6 +136,7 @@ files:
108
136
  - lib/cupper.rb
109
137
  - lib/cupper/cli.rb
110
138
  - lib/cupper/collect.rb
139
+ - lib/cupper/config/config.rb
111
140
  - lib/cupper/cookbook.rb
112
141
  - lib/cupper/cookbook_file.rb
113
142
  - lib/cupper/cupperfile.rb
@@ -127,7 +156,7 @@ files:
127
156
  - lib/cupper/plugins/ohai/services.rb
128
157
  - lib/cupper/project.rb
129
158
  - lib/cupper/recipe.rb
130
- - lib/cupper/templates/CupperFile.erb
159
+ - lib/cupper/templates/Cupperfile.erb
131
160
  - lib/cupper/templates/_cookbook_file.erb
132
161
  - lib/cupper/templates/_groups.erb
133
162
  - lib/cupper/templates/_links.erb
@@ -137,6 +166,7 @@ files:
137
166
  - lib/cupper/templates/_users.erb
138
167
  - lib/cupper/templates/cookbook_file.erb
139
168
  - lib/cupper/templates/recipe.erb
169
+ - lib/cupper/templates/sensibles.erb
140
170
  - lib/cupper/version.rb
141
171
  - templates/locales/en.yml
142
172
  homepage: https://github.com/cupper-reverse-recipe/cupper
@@ -1 +0,0 @@
1
- # Cupper config file