berkshelf-vagrant 1.0.0.rc1
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitignore +17 -0
- data/.travis.yml +12 -0
- data/CHANGELOG.md +3 -0
- data/CONTRIBUTING.md +44 -0
- data/Gemfile +40 -0
- data/Guardfile +16 -0
- data/LICENSE.txt +13 -0
- data/README.md +28 -0
- data/Thorfile +58 -0
- data/berkshelf-vagrant.gemspec +34 -0
- data/lib/berkshelf-vagrant.rb +1 -0
- data/lib/berkshelf/vagrant.rb +40 -0
- data/lib/berkshelf/vagrant/action.rb +61 -0
- data/lib/berkshelf/vagrant/action/clean.rb +26 -0
- data/lib/berkshelf/vagrant/action/configure_chef.rb +22 -0
- data/lib/berkshelf/vagrant/action/install.rb +34 -0
- data/lib/berkshelf/vagrant/action/load_shelf.rb +44 -0
- data/lib/berkshelf/vagrant/action/set_ui.rb +15 -0
- data/lib/berkshelf/vagrant/action/upload.rb +38 -0
- data/lib/berkshelf/vagrant/config.rb +66 -0
- data/lib/berkshelf/vagrant/env.rb +20 -0
- data/lib/berkshelf/vagrant/env_helpers.rb +46 -0
- data/lib/berkshelf/vagrant/errors.rb +33 -0
- data/lib/berkshelf/vagrant/plugin.rb +32 -0
- data/lib/berkshelf/vagrant/version.rb +5 -0
- data/spec/spec_helper.rb +34 -0
- data/spec/unit/berkshelf/vagrant/errors_spec.rb +12 -0
- data/spec/unit/berkshelf/vagrant_spec.rb +25 -0
- metadata +228 -0
data/.gitignore
ADDED
data/.travis.yml
ADDED
data/CHANGELOG.md
ADDED
data/CONTRIBUTING.md
ADDED
@@ -0,0 +1,44 @@
|
|
1
|
+
# Contributing
|
2
|
+
|
3
|
+
## Developing
|
4
|
+
|
5
|
+
If you'd like to submit a patch:
|
6
|
+
|
7
|
+
1. Fork the project.
|
8
|
+
2. Make your feature addition or bug fix.
|
9
|
+
3. Add [tests](#testing) for it. This is important so that it isn't broken in a
|
10
|
+
future version unintentionally.
|
11
|
+
4. Commit. **Do not touch any unrelated code, such as the gemspec or version.**
|
12
|
+
If you must change unrelated code, do it in a commit by itself, so that it
|
13
|
+
can be ignored.
|
14
|
+
5. Send a pull request.
|
15
|
+
|
16
|
+
## Testing
|
17
|
+
|
18
|
+
### Install prerequisites
|
19
|
+
|
20
|
+
Install the latest version of [Bundler](http://gembundler.com)
|
21
|
+
|
22
|
+
$ gem install bundler
|
23
|
+
|
24
|
+
Clone the project
|
25
|
+
|
26
|
+
$ git clone git://github.com/RiotGames/berkshelf-vagrant.git
|
27
|
+
|
28
|
+
and run:
|
29
|
+
|
30
|
+
$ cd berkshelf-vagrant
|
31
|
+
$ bundle-vagrant install
|
32
|
+
|
33
|
+
Bundler will install all gems and their dependencies required for testing and developing.
|
34
|
+
|
35
|
+
### Running unit (RSpec) tests
|
36
|
+
|
37
|
+
One-time run with Thor
|
38
|
+
|
39
|
+
$ bundle exec thor spec
|
40
|
+
|
41
|
+
Or you can setup a quick feedback loop with Guard
|
42
|
+
|
43
|
+
$ bundle exec guard start
|
44
|
+
guard> rspec
|
data/Gemfile
ADDED
@@ -0,0 +1,40 @@
|
|
1
|
+
source 'https://rubygems.org'
|
2
|
+
|
3
|
+
# Specify your gem's dependencies in berkshelf-vagrant.gemspec
|
4
|
+
gemspec
|
5
|
+
|
6
|
+
group :development do
|
7
|
+
gem 'vagrant', github: "mitchellh/vagrant", tag: "v1.1.2"
|
8
|
+
end
|
9
|
+
|
10
|
+
group :test do
|
11
|
+
gem 'coolline'
|
12
|
+
gem 'guard', '>= 1.5.0'
|
13
|
+
gem 'guard-rspec'
|
14
|
+
gem 'guard-spork'
|
15
|
+
gem 'guard-yard'
|
16
|
+
gem 'redcarpet'
|
17
|
+
gem 'yard'
|
18
|
+
gem 'fuubar'
|
19
|
+
gem 'rspec'
|
20
|
+
|
21
|
+
require 'rbconfig'
|
22
|
+
|
23
|
+
if RbConfig::CONFIG['target_os'] =~ /darwin/i
|
24
|
+
gem 'growl', require: false
|
25
|
+
gem 'rb-fsevent', require: false
|
26
|
+
|
27
|
+
if `uname`.strip == 'Darwin' && `sw_vers -productVersion`.strip >= '10.8'
|
28
|
+
gem 'terminal-notifier-guard', '~> 1.5.3', require: false
|
29
|
+
end rescue Errno::ENOENT
|
30
|
+
|
31
|
+
elsif RbConfig::CONFIG['target_os'] =~ /linux/i
|
32
|
+
gem 'libnotify', '~> 0.8.0', require: false
|
33
|
+
gem 'rb-inotify', require: false
|
34
|
+
|
35
|
+
elsif RbConfig::CONFIG['target_os'] =~ /mswin|mingw/i
|
36
|
+
gem 'rb-notifu', '>= 0.0.4', require: false
|
37
|
+
gem 'wdm', require: false
|
38
|
+
gem 'win32console', require: false
|
39
|
+
end
|
40
|
+
end
|
data/Guardfile
ADDED
@@ -0,0 +1,16 @@
|
|
1
|
+
guard 'spork' do
|
2
|
+
watch('Gemfile')
|
3
|
+
watch('spec/spec_helper.rb') { :rspec }
|
4
|
+
end
|
5
|
+
|
6
|
+
guard 'yard', stdout: '/dev/null', stderr: '/dev/null' do
|
7
|
+
watch(%r{app/.+\.rb})
|
8
|
+
watch(%r{lib/.+\.rb})
|
9
|
+
watch(%r{ext/.+\.c})
|
10
|
+
end
|
11
|
+
|
12
|
+
guard 'rspec', cli: "--color --drb --format Fuubar", all_on_start: false, all_after_pass: false do
|
13
|
+
watch(%r{^spec/unit/.+_spec\.rb$})
|
14
|
+
watch(%r{^lib/(.+)\.rb$}) { |m| "spec/unit/#{m[1]}_spec.rb" }
|
15
|
+
watch('spec/spec_helper.rb') { "spec" }
|
16
|
+
end
|
data/LICENSE.txt
ADDED
@@ -0,0 +1,13 @@
|
|
1
|
+
Copyright (c) 2012-2013 Riot Games
|
2
|
+
|
3
|
+
Licensed under the Apache License, Version 2.0 (the "License");
|
4
|
+
you may not use this file except in compliance with the License.
|
5
|
+
You may obtain a copy of the License at
|
6
|
+
|
7
|
+
http://www.apache.org/licenses/LICENSE-2.0
|
8
|
+
|
9
|
+
Unless required by applicable law or agreed to in writing, software
|
10
|
+
distributed under the License is distributed on an "AS IS" BASIS,
|
11
|
+
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
12
|
+
See the License for the specific language governing permissions and
|
13
|
+
limitations under the License.
|
data/README.md
ADDED
@@ -0,0 +1,28 @@
|
|
1
|
+
# Berkshelf::Vagrant
|
2
|
+
[![Gem Version](https://badge.fury.io/rb/berkshelf-vagrant.png)](http://badge.fury.io/rb/berkshelf-vagrant)
|
3
|
+
[![Build Status](https://travis-ci.org/RiotGames/berkshelf-vagrant.png?branch=master)](https://travis-ci.org/RiotGames/berkshelf-vagrant)
|
4
|
+
[![Dependency Status](https://gemnasium.com/RiotGames/berkshelf-vagrant.png)](https://gemnasium.com/RiotGames/berkshelf-vagrant)
|
5
|
+
[![Code Climate](https://codeclimate.com/github/RiotGames/berkshelf-vagrant.png)](https://codeclimate.com/github/RiotGames/berkshelf-vagrant)
|
6
|
+
|
7
|
+
A Vagrant plugin to add Berkshelf integration to the Chef provisioners
|
8
|
+
|
9
|
+
## Installation
|
10
|
+
|
11
|
+
Install Vagrant 1.1.x from the [Vagrant downloads page](http://downloads.vagrantup.com/)
|
12
|
+
|
13
|
+
Install the Berkshelf Vagrant plugin
|
14
|
+
|
15
|
+
$ vagrant plugin install berkshelf-vagrant
|
16
|
+
|
17
|
+
## Usage
|
18
|
+
|
19
|
+
The Berkshelf Vagrant plugin automatically hooks into the Vagrant provisioning middleware; theres no need to perform any additional steps after installation.
|
20
|
+
|
21
|
+
Just ensure that you have a Berksfile in the directory with your Vagrantfile and when you run `vagrant up`, `vagrant provision`, or `vagrant destroy` the Berkshelf integration will automatically kick in!
|
22
|
+
|
23
|
+
# Authors
|
24
|
+
- Jamie Winsor (<reset@riotgames.com>)
|
25
|
+
|
26
|
+
Thank you to all of our [Contributors](https://github.com/RiotGames/berkshelf-vagrant/graphs/contributors), testers, and users.
|
27
|
+
|
28
|
+
If you'd like to contribute, please see our [contribution guidelines](https://github.com/RiotGames/berkshelf-vagrant/blob/master/CONTRIBUTING.md) first.
|
data/Thorfile
ADDED
@@ -0,0 +1,58 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
$:.push File.expand_path("../lib", __FILE__)
|
3
|
+
|
4
|
+
require 'bundler'
|
5
|
+
require 'bundler/setup'
|
6
|
+
require 'thor/rake_compat'
|
7
|
+
|
8
|
+
require 'berkshelf/vagrant'
|
9
|
+
|
10
|
+
class Default < Thor
|
11
|
+
class Gem < Thor
|
12
|
+
include Thor::RakeCompat
|
13
|
+
Bundler::GemHelper.install_tasks
|
14
|
+
|
15
|
+
namespace :gem
|
16
|
+
|
17
|
+
desc "build", "Build berkshelf-vagrant-#{Berkshelf::Vagrant::VERSION}.gem into the pkg directory"
|
18
|
+
def build
|
19
|
+
Rake::Task["build"].execute
|
20
|
+
end
|
21
|
+
|
22
|
+
desc "release", "Create tag v#{Berkshelf::Vagrant::VERSION} and build and push berkshelf-vagrant-#{Berkshelf::Vagrant::VERSION}.gem to Rubygems"
|
23
|
+
def release
|
24
|
+
Rake::Task["release"].execute
|
25
|
+
end
|
26
|
+
|
27
|
+
desc "install", "Build and install berkshelf-vagrant-#{Berkshelf::Vagrant::VERSION}.gem into system gems"
|
28
|
+
def install
|
29
|
+
Rake::Task["install"].execute
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
class Spec < Thor
|
34
|
+
include Thor::Actions
|
35
|
+
|
36
|
+
namespace :spec
|
37
|
+
default_task :unit
|
38
|
+
|
39
|
+
desc "ci", "Run all possible tests on Travis-CI"
|
40
|
+
def ci
|
41
|
+
ENV['CI'] = 'true' # Travis-CI also sets this, but set it here for local testing
|
42
|
+
invoke(:unit)
|
43
|
+
end
|
44
|
+
|
45
|
+
desc "unit", "Run unit tests"
|
46
|
+
def unit
|
47
|
+
unless run_unit
|
48
|
+
exit 1
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
52
|
+
no_tasks do
|
53
|
+
def run_unit(*flags)
|
54
|
+
run "rspec --color --format=documentation #{flags.join(' ')} spec"
|
55
|
+
end
|
56
|
+
end
|
57
|
+
end
|
58
|
+
end
|
@@ -0,0 +1,34 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
lib = File.expand_path('../lib', __FILE__)
|
3
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
|
+
require 'berkshelf/vagrant/version'
|
5
|
+
|
6
|
+
Gem::Specification.new do |spec|
|
7
|
+
spec.name = "berkshelf-vagrant"
|
8
|
+
spec.version = Berkshelf::Vagrant::VERSION
|
9
|
+
spec.authors = [ "Jamie Winsor" ]
|
10
|
+
spec.email = [ "reset@riotgames.com" ]
|
11
|
+
spec.description = %q{A Vagrant plugin to add Berkshelf integration to the Chef provisioners}
|
12
|
+
spec.summary = spec.description
|
13
|
+
spec.homepage = "http://berkshelf.com"
|
14
|
+
spec.license = "Apache 2.0"
|
15
|
+
|
16
|
+
spec.files = `git ls-files`.split($/)
|
17
|
+
spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
|
18
|
+
spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
|
19
|
+
spec.require_paths = ["lib"]
|
20
|
+
spec.required_ruby_version = ">= 1.9.1"
|
21
|
+
|
22
|
+
spec.add_dependency 'berkshelf', '>= 1.3.0.rc1'
|
23
|
+
|
24
|
+
# Explicit locks to ensure we activate the proper gem versions for Vagrant
|
25
|
+
spec.add_dependency "i18n", "~> 0.6.0"
|
26
|
+
spec.add_dependency "json", ">= 1.5.1", "< 1.8.0"
|
27
|
+
spec.add_dependency "net-ssh", "~> 2.6.6"
|
28
|
+
spec.add_dependency "net-scp", "~> 1.1.0"
|
29
|
+
|
30
|
+
spec.add_development_dependency 'bundler', '~> 1.3'
|
31
|
+
spec.add_development_dependency 'spork'
|
32
|
+
spec.add_development_dependency 'rspec'
|
33
|
+
spec.add_development_dependency 'thor'
|
34
|
+
end
|
@@ -0,0 +1 @@
|
|
1
|
+
require 'berkshelf/vagrant'
|
@@ -0,0 +1,40 @@
|
|
1
|
+
require 'vagrant'
|
2
|
+
require 'berkshelf'
|
3
|
+
require 'berkshelf/vagrant/version'
|
4
|
+
require 'berkshelf/vagrant/errors'
|
5
|
+
require 'tmpdir'
|
6
|
+
require 'fileutils'
|
7
|
+
|
8
|
+
module Berkshelf
|
9
|
+
# @author Jamie Winsor <reset@riotgames.com>
|
10
|
+
module Vagrant
|
11
|
+
autoload :Action, 'berkshelf/vagrant/action'
|
12
|
+
autoload :Config, 'berkshelf/vagrant/config'
|
13
|
+
autoload :Env, 'berkshelf/vagrant/env'
|
14
|
+
autoload :EnvHelpers, 'berkshelf/vagrant/env_helpers'
|
15
|
+
|
16
|
+
class << self
|
17
|
+
# The path to where shelfs are created on the host machine to be mounted in
|
18
|
+
# Vagrant guests
|
19
|
+
#
|
20
|
+
# @return [String]
|
21
|
+
def shelf_path
|
22
|
+
File.join(Berkshelf.berkshelf_path, 'vagrant')
|
23
|
+
end
|
24
|
+
|
25
|
+
# Generate a new shelf to be mounted in a Vagrant guest
|
26
|
+
#
|
27
|
+
# @return [String]
|
28
|
+
# path to the generated shelf
|
29
|
+
def mkshelf
|
30
|
+
unless File.exist?(shelf_path)
|
31
|
+
FileUtils.mkdir_p(shelf_path)
|
32
|
+
end
|
33
|
+
|
34
|
+
Dir.mktmpdir('berkshelf-', shelf_path)
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
require 'berkshelf/vagrant/plugin'
|
@@ -0,0 +1,61 @@
|
|
1
|
+
module Berkshelf::Vagrant
|
2
|
+
module Action
|
3
|
+
autoload :Clean, 'berkshelf/vagrant/action/clean'
|
4
|
+
autoload :ConfigureChef, 'berkshelf/vagrant/action/configure_chef'
|
5
|
+
autoload :Install, 'berkshelf/vagrant/action/install'
|
6
|
+
autoload :LoadShelf, 'berkshelf/vagrant/action/load_shelf'
|
7
|
+
autoload :SetUI, 'berkshelf/vagrant/action/set_ui'
|
8
|
+
autoload :Upload, 'berkshelf/vagrant/action/upload'
|
9
|
+
|
10
|
+
class << self
|
11
|
+
# Return the Berkshelf install middleware stack. When placed in the action chain
|
12
|
+
# this stack will find retrieve and resolve the cookbook dependencies describe
|
13
|
+
# in your configured Berksfile.
|
14
|
+
#
|
15
|
+
# Cookbooks will installed into a temporary directory, called a Shelf, and mounted
|
16
|
+
# into the VM. This mounted path will be appended to the chef_solo.cookbooks_path value.
|
17
|
+
#
|
18
|
+
# @return [::Vagrant::Action::Builder]
|
19
|
+
def install
|
20
|
+
@install ||= ::Vagrant::Action::Builder.new.tap do |b|
|
21
|
+
b.use Berkshelf::Vagrant::Action::Install
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
# Return the Berkshelf upload middleware stack. When placed in the action chain
|
26
|
+
# this stack will upload cookbooks to a Chef Server if the Chef-Client provisioner
|
27
|
+
# is used. The Chef Server where the cookbooks will be uploaded to is the same Chef
|
28
|
+
# Server used in the Chef-Client provisioner.
|
29
|
+
#
|
30
|
+
# Nothing will be done if the Chef-Solo provisioner is used.
|
31
|
+
#
|
32
|
+
# @return [::Vagrant::Action::Builder]
|
33
|
+
def upload
|
34
|
+
@upload ||= ::Vagrant::Action::Builder.new.tap do |b|
|
35
|
+
b.use Berkshelf::Vagrant::Action::Upload
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
# Return the Berkshelf clean middleware stack. When placed in the action chain
|
40
|
+
# this stack will clean up any temporary directories or files created by the other
|
41
|
+
# middleware stacks.
|
42
|
+
#
|
43
|
+
# @return [::Vagrant::Action::Builder]
|
44
|
+
def clean
|
45
|
+
@clean ||= ::Vagrant::Action::Builder.new.tap do |b|
|
46
|
+
b.use setup
|
47
|
+
b.use Berkshelf::Vagrant::Action::Clean
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
def setup
|
52
|
+
@setup ||= ::Vagrant::Action::Builder.new.tap do |b|
|
53
|
+
b.use ::Vagrant::Action::Builtin::EnvSet, berkshelf: Berkshelf::Vagrant::Env.new
|
54
|
+
b.use Berkshelf::Vagrant::Action::SetUI
|
55
|
+
b.use Berkshelf::Vagrant::Action::LoadShelf
|
56
|
+
b.use Berkshelf::Vagrant::Action::ConfigureChef
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|
@@ -0,0 +1,26 @@
|
|
1
|
+
module Berkshelf::Vagrant
|
2
|
+
module Action
|
3
|
+
# @author Jamie Winsor <reset@riotgames.com>
|
4
|
+
class Clean
|
5
|
+
include Berkshelf::Vagrant::EnvHelpers
|
6
|
+
|
7
|
+
def initialize(app, env)
|
8
|
+
@app = app
|
9
|
+
end
|
10
|
+
|
11
|
+
def call(env)
|
12
|
+
if env[:berkshelf].shelf && File.exist?(env[:berkshelf].shelf)
|
13
|
+
env[:berkshelf].ui.info "Cleaning Vagrant's berkshelf"
|
14
|
+
|
15
|
+
FileUtils.remove_dir(env[:berkshelf].shelf, force: true)
|
16
|
+
FileUtils.rm_f(cache_file)
|
17
|
+
env[:berkshelf].shelf = nil
|
18
|
+
end
|
19
|
+
|
20
|
+
@app.call(env)
|
21
|
+
rescue Berkshelf::BerkshelfError => e
|
22
|
+
raise VagrantWrapperError.new(e)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
module Berkshelf::Vagrant
|
2
|
+
module Action
|
3
|
+
# @author Jamie Winsor <reset@riotgames.com>
|
4
|
+
class ConfigureChef
|
5
|
+
include Berkshelf::Vagrant::EnvHelpers
|
6
|
+
|
7
|
+
def initialize(app, env)
|
8
|
+
@app = app
|
9
|
+
end
|
10
|
+
|
11
|
+
def call(env)
|
12
|
+
if chef_solo?(env) && env[:berkshelf].shelf
|
13
|
+
provisioners(:chef_solo, env).each do |provisioner|
|
14
|
+
provisioner.config.cookbooks_path = provisioner.config.send(:prepare_folders_config, env[:berkshelf].shelf)
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
@app.call(env)
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,34 @@
|
|
1
|
+
module Berkshelf::Vagrant
|
2
|
+
module Action
|
3
|
+
# @author Jamie Winsor <reset@riotgames.com>
|
4
|
+
class Install
|
5
|
+
include Berkshelf::Vagrant::EnvHelpers
|
6
|
+
|
7
|
+
def initialize(app, env)
|
8
|
+
@app = app
|
9
|
+
end
|
10
|
+
|
11
|
+
def call(env)
|
12
|
+
env[:berkshelf].berksfile = Berkshelf::Berksfile.from_file(env[:global_config].berkshelf.berksfile_path)
|
13
|
+
|
14
|
+
if chef_solo?(env)
|
15
|
+
install(env)
|
16
|
+
end
|
17
|
+
|
18
|
+
@app.call(env)
|
19
|
+
rescue Berkshelf::BerkshelfError => e
|
20
|
+
raise VagrantWrapperError.new(e)
|
21
|
+
end
|
22
|
+
|
23
|
+
private
|
24
|
+
|
25
|
+
def install(env)
|
26
|
+
env[:berkshelf].ui.info "Updating Vagrant's berkshelf: '#{env[:berkshelf].shelf}'"
|
27
|
+
opts = {
|
28
|
+
path: env[:berkshelf].shelf
|
29
|
+
}.merge(env[:global_config].berkshelf.to_hash).symbolize_keys!
|
30
|
+
env[:berkshelf].berksfile.install(opts)
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
@@ -0,0 +1,44 @@
|
|
1
|
+
module Berkshelf::Vagrant
|
2
|
+
module Action
|
3
|
+
# @author Jamie Winsor <reset@riotgames.com>
|
4
|
+
class LoadShelf
|
5
|
+
include Berkshelf::Vagrant::EnvHelpers
|
6
|
+
|
7
|
+
def initialize(app, env)
|
8
|
+
@app = app
|
9
|
+
end
|
10
|
+
|
11
|
+
def call(env)
|
12
|
+
shelf = load_shelf
|
13
|
+
|
14
|
+
if shelf.nil?
|
15
|
+
shelf = cache_shelf(Berkshelf::Vagrant.mkshelf)
|
16
|
+
end
|
17
|
+
|
18
|
+
env[:berkshelf].shelf = shelf
|
19
|
+
|
20
|
+
@app.call(env)
|
21
|
+
end
|
22
|
+
|
23
|
+
# @param [String] path
|
24
|
+
#
|
25
|
+
# @return [String]
|
26
|
+
def cache_shelf(path)
|
27
|
+
FileUtils.mkdir_p(File.dirname(path))
|
28
|
+
|
29
|
+
File.open(cache_file, 'w+') do |f|
|
30
|
+
f.write(path)
|
31
|
+
end
|
32
|
+
|
33
|
+
path
|
34
|
+
end
|
35
|
+
|
36
|
+
# @return [String, nil]
|
37
|
+
def load_shelf
|
38
|
+
return nil unless File.exist?(cache_file)
|
39
|
+
|
40
|
+
File.read(cache_file).chomp
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
@@ -0,0 +1,38 @@
|
|
1
|
+
module Berkshelf::Vagrant
|
2
|
+
module Action
|
3
|
+
# @author Jamie Winsor <reset@riotgames.com>
|
4
|
+
class Upload
|
5
|
+
include Berkshelf::Vagrant::EnvHelpers
|
6
|
+
|
7
|
+
def initialize(app, env)
|
8
|
+
@app = app
|
9
|
+
end
|
10
|
+
|
11
|
+
def call(env)
|
12
|
+
if chef_client?(env)
|
13
|
+
upload(env)
|
14
|
+
end
|
15
|
+
|
16
|
+
@app.call(env)
|
17
|
+
rescue Berkshelf::BerkshelfError => e
|
18
|
+
raise VagrantWrapperError.new(e)
|
19
|
+
end
|
20
|
+
|
21
|
+
private
|
22
|
+
|
23
|
+
def upload(env)
|
24
|
+
provisioners(:chef_client, env).each do |provisioner|
|
25
|
+
env[:berkshelf].ui.info "Uploading cookbooks to '#{provisioner.config.chef_server_url}'"
|
26
|
+
env[:berkshelf].berksfile.upload(
|
27
|
+
server_url: provisioner.config.chef_server_url,
|
28
|
+
client_name: env[:berkshelf].config.chef.node_name,
|
29
|
+
client_key: env[:berkshelf].config.chef.client_key,
|
30
|
+
ssl: {
|
31
|
+
verify: env[:berkshelf].config.ssl.verify
|
32
|
+
}
|
33
|
+
)
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
@@ -0,0 +1,66 @@
|
|
1
|
+
module Berkshelf
|
2
|
+
module Vagrant
|
3
|
+
# @author Jamie Winsor <reset@riotgames.com>
|
4
|
+
class Config < ::Vagrant.plugin("2", :config)
|
5
|
+
include Berkshelf::Vagrant::EnvHelpers
|
6
|
+
|
7
|
+
# @return [String]
|
8
|
+
# path to the Berksfile to use with Vagrant
|
9
|
+
attr_reader :berksfile_path
|
10
|
+
|
11
|
+
# @return [Array<Symbol>]
|
12
|
+
# only cookbooks in these groups will be installed and copied to
|
13
|
+
# Vagrant's shelf
|
14
|
+
attr_accessor :only
|
15
|
+
|
16
|
+
# @return [Array<Symbol>]
|
17
|
+
# cookbooks in all other groups except for these will be installed
|
18
|
+
# and copied to Vagrant's shelf
|
19
|
+
attr_accessor :except
|
20
|
+
|
21
|
+
def initialize
|
22
|
+
@berksfile_path = UNSET_VALUE
|
23
|
+
@except = UNSET_VALUE
|
24
|
+
@only = UNSET_VALUE
|
25
|
+
end
|
26
|
+
|
27
|
+
def finalize!
|
28
|
+
@berksfile_path = File.join(Dir.pwd, Berkshelf::DEFAULT_FILENAME) if @berksfile_path == UNSET_VALUE
|
29
|
+
@except = Array.new if @except == UNSET_VALUE
|
30
|
+
@only = Array.new if @only == UNSET_VALUE
|
31
|
+
end
|
32
|
+
|
33
|
+
# @param [String] value
|
34
|
+
def berksfile_path=(value)
|
35
|
+
@berksfile_path = File.expand_path(value)
|
36
|
+
end
|
37
|
+
|
38
|
+
# @param [String] value
|
39
|
+
def client_key=(value)
|
40
|
+
@client_key = File.expand_path(value)
|
41
|
+
end
|
42
|
+
|
43
|
+
alias_method :to_hash, :instance_variables_hash
|
44
|
+
|
45
|
+
def validate(machine)
|
46
|
+
errors = Array.new
|
47
|
+
|
48
|
+
if !except.empty? && !only.empty?
|
49
|
+
errors.add("A value for berkshelf.empty and berkshelf.only cannot both be defined.")
|
50
|
+
end
|
51
|
+
|
52
|
+
if chef_client?(machine.env)
|
53
|
+
if Berkshelf::Config.instance.chef.node_name.nil?
|
54
|
+
errors.add("A configuration must be set for chef.node_name when using the chef_client provisioner. Run 'berks configure' or edit your configuration.")
|
55
|
+
end
|
56
|
+
|
57
|
+
if Berkshelf::Config.instance.chef.client_key.nil?
|
58
|
+
errors.add("A configuration must be set for chef.client_key when using the chef_client provisioner. Run 'berks configure' or edit your configuration.")
|
59
|
+
end
|
60
|
+
end
|
61
|
+
|
62
|
+
{ "berkshelf configuration" => errors }
|
63
|
+
end
|
64
|
+
end
|
65
|
+
end
|
66
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
module Berkshelf::Vagrant
|
2
|
+
# @author Jamie Winsor <reset@riotgames.com>
|
3
|
+
#
|
4
|
+
# Environment data to build up and persist through the middleware chain
|
5
|
+
class Env
|
6
|
+
# @return [Vagrant::UI::Colored]
|
7
|
+
attr_accessor :ui
|
8
|
+
# @return [Berkshelf::Berksfile]
|
9
|
+
attr_accessor :berksfile
|
10
|
+
# @return [String]
|
11
|
+
attr_accessor :shelf
|
12
|
+
# @return [Berkshelf::Config]
|
13
|
+
attr_accessor :config
|
14
|
+
|
15
|
+
def initialize
|
16
|
+
@ui = ::Vagrant::UI::Colored.new('Berkshelf')
|
17
|
+
@config = Berkshelf::Config.instance
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,46 @@
|
|
1
|
+
module Berkshelf::Vagrant
|
2
|
+
# @author Jamie Winsor <reset@riotgames.com>
|
3
|
+
#
|
4
|
+
# A module of common helper functions that can be mixed into Berkshelf::Vagrant actions
|
5
|
+
module EnvHelpers
|
6
|
+
# A file to persist berkshelf-vagrant specific information in between
|
7
|
+
# Vagrant runs.
|
8
|
+
#
|
9
|
+
# @return [String]
|
10
|
+
def cache_file
|
11
|
+
File.join('.vagrant', 'berkshelf')
|
12
|
+
end
|
13
|
+
|
14
|
+
# Filter all of the provisioners of the given vagrant environment with the given name
|
15
|
+
#
|
16
|
+
# @param [Symbol] name
|
17
|
+
# name of provisioner to filter
|
18
|
+
# @param [Vagrant::Environment, Hash] env
|
19
|
+
# environment to inspect
|
20
|
+
#
|
21
|
+
# @return [Array]
|
22
|
+
def provisioners(name, env)
|
23
|
+
config_global = env.respond_to?(:config_global) ? env.config_global : env[:global_config]
|
24
|
+
|
25
|
+
config_global.vm.provisioners.select { |prov| prov.name == name }
|
26
|
+
end
|
27
|
+
|
28
|
+
# Determine if the given vagrant environment contains a chef_solo provisioner
|
29
|
+
#
|
30
|
+
# @param [Vagrant::Environment] env
|
31
|
+
#
|
32
|
+
# @return [Boolean]
|
33
|
+
def chef_solo?(env)
|
34
|
+
provisioners(:chef_solo, env).any?
|
35
|
+
end
|
36
|
+
|
37
|
+
# Determine if the given vagrant environment contains a chef_client provisioner
|
38
|
+
#
|
39
|
+
# @param [Vagrant::Environment] env
|
40
|
+
#
|
41
|
+
# @return [Boolean]
|
42
|
+
def chef_client?(env)
|
43
|
+
provisioners(:chef_client, env).any?
|
44
|
+
end
|
45
|
+
end
|
46
|
+
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
require 'vagrant/errors'
|
2
|
+
|
3
|
+
module Berkshelf
|
4
|
+
# @author Jamie Winsor <reset@riotgames.com>
|
5
|
+
#
|
6
|
+
# A wrapper for a BerkshelfError for Vagrant. All Berkshelf exceptions should be
|
7
|
+
# wrapped in this proxy object so they are properly handled when Vagrant encounters
|
8
|
+
# an exception.
|
9
|
+
#
|
10
|
+
# @example wrapping an error encountered within the Vagrant plugin
|
11
|
+
# rescue BerkshelfError => e
|
12
|
+
# VagrantWrapperError.new(e)
|
13
|
+
# end
|
14
|
+
class VagrantWrapperError < ::Vagrant::Errors::VagrantError
|
15
|
+
# @param [BerkshelfError]
|
16
|
+
attr_reader :original
|
17
|
+
|
18
|
+
# @param [BerkshelfError] original
|
19
|
+
def initialize(original)
|
20
|
+
@original = original
|
21
|
+
end
|
22
|
+
|
23
|
+
def to_s
|
24
|
+
"#{original.class}: #{original.to_s}"
|
25
|
+
end
|
26
|
+
|
27
|
+
private
|
28
|
+
|
29
|
+
def method_missing(fun, *args, &block)
|
30
|
+
original.send(fun, *args, &block)
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -0,0 +1,32 @@
|
|
1
|
+
module Berkshelf::Vagrant
|
2
|
+
# @author Jamie Winsor <reset@riotgames.com>
|
3
|
+
class Plugin < ::Vagrant.plugin("2")
|
4
|
+
class << self
|
5
|
+
def provision(hook)
|
6
|
+
hook.after(Vagrant::Action::Builtin::Provision, Berkshelf::Vagrant::Action.upload)
|
7
|
+
hook.after(Vagrant::Action::Builtin::Provision, Berkshelf::Vagrant::Action.install)
|
8
|
+
hook.before(Vagrant::Action::Builtin::ConfigValidate, Berkshelf::Vagrant::Action.setup)
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
name "berkshelf"
|
13
|
+
description <<-DESC
|
14
|
+
Automatically make available cookbooks to virtual machines provisioned by Chef Solo
|
15
|
+
or Chef Client using Berkshelf.
|
16
|
+
DESC
|
17
|
+
|
18
|
+
action_hook(:berkshelf_provision, :machine_action_up, &method(:provision))
|
19
|
+
action_hook(:berkshelf_provision, :machine_action_provision, &method(:provision))
|
20
|
+
|
21
|
+
action_hook(:berkshelf_cleanup, :machine_action_destroy) do |hook|
|
22
|
+
# @todo this should be appended to the middleware stack instead of hooked in after the
|
23
|
+
# Virtualbox specific destroy step but there is a bug in Vagrant (1.1.0) which
|
24
|
+
# causes appended middleware to run multiple times.
|
25
|
+
hook.after(VagrantPlugins::ProviderVirtualBox::Action::DestroyUnusedNetworkInterfaces, Berkshelf::Vagrant::Action.clean)
|
26
|
+
end
|
27
|
+
|
28
|
+
config(:berkshelf) do
|
29
|
+
Berkshelf::Vagrant::Config
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,34 @@
|
|
1
|
+
require 'rubygems'
|
2
|
+
require 'bundler'
|
3
|
+
require 'spork'
|
4
|
+
|
5
|
+
Spork.prefork do
|
6
|
+
APP_ROOT = File.expand_path('../../', __FILE__)
|
7
|
+
ENV["BERKSHELF_PATH"] = File.join(APP_ROOT, 'spec', 'tmp', 'berkshelf')
|
8
|
+
|
9
|
+
require 'rspec'
|
10
|
+
|
11
|
+
RSpec.configure do |config|
|
12
|
+
config.mock_with :rspec
|
13
|
+
config.treat_symbols_as_metadata_keys_with_true_values = true
|
14
|
+
config.filter_run focus: true
|
15
|
+
config.run_all_when_everything_filtered = true
|
16
|
+
|
17
|
+
config.around(:each) do
|
18
|
+
clean_tmp_path
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
def clean_tmp_path
|
23
|
+
FileUtils.rm_rf(tmp_path)
|
24
|
+
FileUtils.mkdir_p(tmp_path)
|
25
|
+
end
|
26
|
+
|
27
|
+
def tmp_path
|
28
|
+
File.join(APP_ROOT, 'spec', 'tmp')
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
Spork.each_run do
|
33
|
+
require 'berkshelf/vagrant'
|
34
|
+
end
|
@@ -0,0 +1,12 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Berkshelf::VagrantWrapperError do
|
4
|
+
subject { described_class }
|
5
|
+
|
6
|
+
it "proxies messages to the original exception" do
|
7
|
+
original = double('original_error')
|
8
|
+
original.should_receive(:a_message)
|
9
|
+
|
10
|
+
subject.new(original).a_message
|
11
|
+
end
|
12
|
+
end
|
@@ -0,0 +1,25 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Berkshelf::Vagrant do
|
4
|
+
describe "ClassMethods" do
|
5
|
+
describe "::shelf_path" do
|
6
|
+
it "returns a String" do
|
7
|
+
subject.shelf_path.should be_a(String)
|
8
|
+
end
|
9
|
+
|
10
|
+
it "is a pathname including the berkshelf_path" do
|
11
|
+
subject.shelf_path.should include(Berkshelf.berkshelf_path)
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
describe "::mkshelf" do
|
16
|
+
it "returns a String" do
|
17
|
+
subject.mkshelf.should be_a(String)
|
18
|
+
end
|
19
|
+
|
20
|
+
it "is a pathname including the shelf_path" do
|
21
|
+
subject.mkshelf.should include(subject.shelf_path)
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
metadata
ADDED
@@ -0,0 +1,228 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: berkshelf-vagrant
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 1.0.0.rc1
|
5
|
+
prerelease: 6
|
6
|
+
platform: ruby
|
7
|
+
authors:
|
8
|
+
- Jamie Winsor
|
9
|
+
autorequire:
|
10
|
+
bindir: bin
|
11
|
+
cert_chain: []
|
12
|
+
date: 2013-03-20 00:00:00.000000000 Z
|
13
|
+
dependencies:
|
14
|
+
- !ruby/object:Gem::Dependency
|
15
|
+
name: berkshelf
|
16
|
+
requirement: !ruby/object:Gem::Requirement
|
17
|
+
none: false
|
18
|
+
requirements:
|
19
|
+
- - ! '>='
|
20
|
+
- !ruby/object:Gem::Version
|
21
|
+
version: 1.3.0.rc1
|
22
|
+
type: :runtime
|
23
|
+
prerelease: false
|
24
|
+
version_requirements: !ruby/object:Gem::Requirement
|
25
|
+
none: false
|
26
|
+
requirements:
|
27
|
+
- - ! '>='
|
28
|
+
- !ruby/object:Gem::Version
|
29
|
+
version: 1.3.0.rc1
|
30
|
+
- !ruby/object:Gem::Dependency
|
31
|
+
name: i18n
|
32
|
+
requirement: !ruby/object:Gem::Requirement
|
33
|
+
none: false
|
34
|
+
requirements:
|
35
|
+
- - ~>
|
36
|
+
- !ruby/object:Gem::Version
|
37
|
+
version: 0.6.0
|
38
|
+
type: :runtime
|
39
|
+
prerelease: false
|
40
|
+
version_requirements: !ruby/object:Gem::Requirement
|
41
|
+
none: false
|
42
|
+
requirements:
|
43
|
+
- - ~>
|
44
|
+
- !ruby/object:Gem::Version
|
45
|
+
version: 0.6.0
|
46
|
+
- !ruby/object:Gem::Dependency
|
47
|
+
name: json
|
48
|
+
requirement: !ruby/object:Gem::Requirement
|
49
|
+
none: false
|
50
|
+
requirements:
|
51
|
+
- - ! '>='
|
52
|
+
- !ruby/object:Gem::Version
|
53
|
+
version: 1.5.1
|
54
|
+
- - <
|
55
|
+
- !ruby/object:Gem::Version
|
56
|
+
version: 1.8.0
|
57
|
+
type: :runtime
|
58
|
+
prerelease: false
|
59
|
+
version_requirements: !ruby/object:Gem::Requirement
|
60
|
+
none: false
|
61
|
+
requirements:
|
62
|
+
- - ! '>='
|
63
|
+
- !ruby/object:Gem::Version
|
64
|
+
version: 1.5.1
|
65
|
+
- - <
|
66
|
+
- !ruby/object:Gem::Version
|
67
|
+
version: 1.8.0
|
68
|
+
- !ruby/object:Gem::Dependency
|
69
|
+
name: net-ssh
|
70
|
+
requirement: !ruby/object:Gem::Requirement
|
71
|
+
none: false
|
72
|
+
requirements:
|
73
|
+
- - ~>
|
74
|
+
- !ruby/object:Gem::Version
|
75
|
+
version: 2.6.6
|
76
|
+
type: :runtime
|
77
|
+
prerelease: false
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
79
|
+
none: false
|
80
|
+
requirements:
|
81
|
+
- - ~>
|
82
|
+
- !ruby/object:Gem::Version
|
83
|
+
version: 2.6.6
|
84
|
+
- !ruby/object:Gem::Dependency
|
85
|
+
name: net-scp
|
86
|
+
requirement: !ruby/object:Gem::Requirement
|
87
|
+
none: false
|
88
|
+
requirements:
|
89
|
+
- - ~>
|
90
|
+
- !ruby/object:Gem::Version
|
91
|
+
version: 1.1.0
|
92
|
+
type: :runtime
|
93
|
+
prerelease: false
|
94
|
+
version_requirements: !ruby/object:Gem::Requirement
|
95
|
+
none: false
|
96
|
+
requirements:
|
97
|
+
- - ~>
|
98
|
+
- !ruby/object:Gem::Version
|
99
|
+
version: 1.1.0
|
100
|
+
- !ruby/object:Gem::Dependency
|
101
|
+
name: bundler
|
102
|
+
requirement: !ruby/object:Gem::Requirement
|
103
|
+
none: false
|
104
|
+
requirements:
|
105
|
+
- - ~>
|
106
|
+
- !ruby/object:Gem::Version
|
107
|
+
version: '1.3'
|
108
|
+
type: :development
|
109
|
+
prerelease: false
|
110
|
+
version_requirements: !ruby/object:Gem::Requirement
|
111
|
+
none: false
|
112
|
+
requirements:
|
113
|
+
- - ~>
|
114
|
+
- !ruby/object:Gem::Version
|
115
|
+
version: '1.3'
|
116
|
+
- !ruby/object:Gem::Dependency
|
117
|
+
name: spork
|
118
|
+
requirement: !ruby/object:Gem::Requirement
|
119
|
+
none: false
|
120
|
+
requirements:
|
121
|
+
- - ! '>='
|
122
|
+
- !ruby/object:Gem::Version
|
123
|
+
version: '0'
|
124
|
+
type: :development
|
125
|
+
prerelease: false
|
126
|
+
version_requirements: !ruby/object:Gem::Requirement
|
127
|
+
none: false
|
128
|
+
requirements:
|
129
|
+
- - ! '>='
|
130
|
+
- !ruby/object:Gem::Version
|
131
|
+
version: '0'
|
132
|
+
- !ruby/object:Gem::Dependency
|
133
|
+
name: rspec
|
134
|
+
requirement: !ruby/object:Gem::Requirement
|
135
|
+
none: false
|
136
|
+
requirements:
|
137
|
+
- - ! '>='
|
138
|
+
- !ruby/object:Gem::Version
|
139
|
+
version: '0'
|
140
|
+
type: :development
|
141
|
+
prerelease: false
|
142
|
+
version_requirements: !ruby/object:Gem::Requirement
|
143
|
+
none: false
|
144
|
+
requirements:
|
145
|
+
- - ! '>='
|
146
|
+
- !ruby/object:Gem::Version
|
147
|
+
version: '0'
|
148
|
+
- !ruby/object:Gem::Dependency
|
149
|
+
name: thor
|
150
|
+
requirement: !ruby/object:Gem::Requirement
|
151
|
+
none: false
|
152
|
+
requirements:
|
153
|
+
- - ! '>='
|
154
|
+
- !ruby/object:Gem::Version
|
155
|
+
version: '0'
|
156
|
+
type: :development
|
157
|
+
prerelease: false
|
158
|
+
version_requirements: !ruby/object:Gem::Requirement
|
159
|
+
none: false
|
160
|
+
requirements:
|
161
|
+
- - ! '>='
|
162
|
+
- !ruby/object:Gem::Version
|
163
|
+
version: '0'
|
164
|
+
description: A Vagrant plugin to add Berkshelf integration to the Chef provisioners
|
165
|
+
email:
|
166
|
+
- reset@riotgames.com
|
167
|
+
executables: []
|
168
|
+
extensions: []
|
169
|
+
extra_rdoc_files: []
|
170
|
+
files:
|
171
|
+
- .gitignore
|
172
|
+
- .travis.yml
|
173
|
+
- CHANGELOG.md
|
174
|
+
- CONTRIBUTING.md
|
175
|
+
- Gemfile
|
176
|
+
- Guardfile
|
177
|
+
- LICENSE.txt
|
178
|
+
- README.md
|
179
|
+
- Thorfile
|
180
|
+
- berkshelf-vagrant.gemspec
|
181
|
+
- lib/berkshelf-vagrant.rb
|
182
|
+
- lib/berkshelf/vagrant.rb
|
183
|
+
- lib/berkshelf/vagrant/action.rb
|
184
|
+
- lib/berkshelf/vagrant/action/clean.rb
|
185
|
+
- lib/berkshelf/vagrant/action/configure_chef.rb
|
186
|
+
- lib/berkshelf/vagrant/action/install.rb
|
187
|
+
- lib/berkshelf/vagrant/action/load_shelf.rb
|
188
|
+
- lib/berkshelf/vagrant/action/set_ui.rb
|
189
|
+
- lib/berkshelf/vagrant/action/upload.rb
|
190
|
+
- lib/berkshelf/vagrant/config.rb
|
191
|
+
- lib/berkshelf/vagrant/env.rb
|
192
|
+
- lib/berkshelf/vagrant/env_helpers.rb
|
193
|
+
- lib/berkshelf/vagrant/errors.rb
|
194
|
+
- lib/berkshelf/vagrant/plugin.rb
|
195
|
+
- lib/berkshelf/vagrant/version.rb
|
196
|
+
- spec/spec_helper.rb
|
197
|
+
- spec/unit/berkshelf/vagrant/errors_spec.rb
|
198
|
+
- spec/unit/berkshelf/vagrant_spec.rb
|
199
|
+
homepage: http://berkshelf.com
|
200
|
+
licenses:
|
201
|
+
- Apache 2.0
|
202
|
+
post_install_message:
|
203
|
+
rdoc_options: []
|
204
|
+
require_paths:
|
205
|
+
- lib
|
206
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
207
|
+
none: false
|
208
|
+
requirements:
|
209
|
+
- - ! '>='
|
210
|
+
- !ruby/object:Gem::Version
|
211
|
+
version: 1.9.1
|
212
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
213
|
+
none: false
|
214
|
+
requirements:
|
215
|
+
- - ! '>'
|
216
|
+
- !ruby/object:Gem::Version
|
217
|
+
version: 1.3.1
|
218
|
+
requirements: []
|
219
|
+
rubyforge_project:
|
220
|
+
rubygems_version: 1.8.24
|
221
|
+
signing_key:
|
222
|
+
specification_version: 3
|
223
|
+
summary: A Vagrant plugin to add Berkshelf integration to the Chef provisioners
|
224
|
+
test_files:
|
225
|
+
- spec/spec_helper.rb
|
226
|
+
- spec/unit/berkshelf/vagrant/errors_spec.rb
|
227
|
+
- spec/unit/berkshelf/vagrant_spec.rb
|
228
|
+
has_rdoc:
|