Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Browse files

Merge pull request #232 from Maher4Ever/master

Add the ability to initialize all guards at once and a --bare option to the init task
  • Loading branch information...
commit 3e854a9dbc20502b660d77350841d86a79244434 2 parents c61a49c + 688100a
Thibaud Guillaume-Gentil authored
View
25 README.md
@@ -201,26 +201,41 @@ $ guard help start
### Init
-You can generate an empty `Guardfile` by running the `init` task:
+You can generate a Guardfile and have all installed guards be automatically added into
+it by running the `init` task without any option:
```bash
$ guard init
```
-In addition, the `init` task can be used to append a supplied Guard template from an installed Guard to your existing
-`Guardfile`:
+You can also specify the name of an installed Guard to only get that Guard
+in the generated Guardfile:
```bash
$ guard init <guard-name>
```
-You can also define your own templates in `~/.guard/templates/` which can be appended in the same way to your existing
+You can also define your own templates in `~/.guard/templates/` which can be appended in the same way to your existing
`Guardfile`:
```bash
$ guard init <template-name>
```
+**Note**: If you already have a `Guardfile` in the current directory, the `init` task can be used
+to append a supplied Guard template from an installed Guard to your existing
+`Guardfile`.
+
+#### `-b`/`--bare` option
+
+You can generate an empty `Guardfile` by running the `init` task with the bare
+option:
+
+```bash
+$ guard init --bare
+$ guard init -b # shortcut
+```
+
### Start
Just launch Guard inside your Ruby or Rails project with:
@@ -832,7 +847,7 @@ When you file an issue, please try to follow to these simple rules if applicable
* Add your `Guardfile` and `Gemfile` to the issue.
* Make sure that the issue is reproducible with your description.
-Development [![Dependency Status](https://gemnasium.com/guard/guard.png?branch=master)](https://gemnasium.com/guard/guard)
+Development [![Dependency Status](https://gemnasium.com/guard/guard.png?branch=master)](https://gemnasium.com/guard/guard)
-----------
* Documentation hosted at [RubyDoc](http://rubydoc.info/github/guard/guard/master/frames).
View
66 lib/guard.rb
@@ -23,44 +23,62 @@ module Guard
class << self
attr_accessor :options, :interactor, :listener, :lock
- # Creates the initial Guardfile template and/or add a Guard implementation
- # Guardfile template to an existing Guardfile.
+ # Creates the initial Guardfile template when it does not
+ # already exist.
#
- # @see Guard::Guard.init
+ # @see Guard::CLI.init
#
- # @param [String] guard_name the name of the Guard or template to initialize
+ # @param [Hash] options The options for creating a Guardfile
+ # @option options [Boolean] :abort_on_existence Whether to abort or not when a Guardfile already exists
#
- def initialize_template(guard_name = nil)
+ def create_guardfile(options = {})
if !File.exist?('Guardfile')
::Guard::UI.info "Writing new Guardfile to #{ Dir.pwd }/Guardfile"
FileUtils.cp(GUARDFILE_TEMPLATE, 'Guardfile')
- elsif guard_name.nil?
+ elsif options[:abort_on_existence]
::Guard::UI.error "Guardfile already exists at #{ Dir.pwd }/Guardfile"
- exit 1
+ abort
end
+ end
- if guard_name
- guard_class = ::Guard.get_guard_class(guard_name, true)
- if guard_class
- guard_class.init(guard_name)
- elsif File.exist?(File.join(HOME_TEMPLATES, guard_name))
- content = File.read('Guardfile')
- template = File.read(File.join(HOME_TEMPLATES, guard_name))
-
- File.open('Guardfile', 'wb') do |f|
- f.puts(content)
- f.puts("")
- f.puts(template)
- end
+ # Adds the Guardfile template of a Guard implementation
+ # to an existing Guardfile.
+ #
+ # @see Guard::CLI.init
+ #
+ # @param [String] guard_name the name of the Guard or template to initialize
+ #
+ def initialize_template(guard_name)
+ guard_class = ::Guard.get_guard_class(guard_name, true)
- ::Guard::UI.info "#{ guard_name } template added to Guardfile, feel free to edit it"
- else
- const_name = guard_name.downcase.gsub('-', '')
- UI.error "Could not load 'guard/#{ guard_name.downcase }' or '~/.guard/templates/#{ guard_name.downcase }' or find class Guard::#{ const_name.capitalize }"
+ if guard_class
+ guard_class.init(guard_name)
+ elsif File.exist?(File.join(HOME_TEMPLATES, guard_name))
+ content = File.read('Guardfile')
+ template = File.read(File.join(HOME_TEMPLATES, guard_name))
+
+ File.open('Guardfile', 'wb') do |f|
+ f.puts(content)
+ f.puts("")
+ f.puts(template)
end
+
+ ::Guard::UI.info "#{ guard_name } template added to Guardfile, feel free to edit it"
+ else
+ const_name = guard_name.downcase.gsub('-', '')
+ UI.error "Could not load 'guard/#{ guard_name.downcase }' or '~/.guard/templates/#{ guard_name.downcase }' or find class Guard::#{ const_name.capitalize }"
end
end
+ # Adds the templates of all installed Guard implementations
+ # to an existing Guardfile.
+ #
+ # @see Guard::CLI.init
+ #
+ def initialize_all_templates
+ guard_gem_names.each {|g| initialize_template(g) }
+ end
+
# Initialize the Guard singleton:
#
# - Initialize the internal Guard state.
View
27 lib/guard/cli.rb
@@ -102,18 +102,35 @@ def version
::Guard::UI.info "Guard version #{ ::Guard::VERSION }"
end
- desc 'init [GUARD]', 'Generates a Guardfile at the current working directory, or insert the given GUARD to an existing Guardfile'
+ desc 'init [GUARD]', 'Generates a Guardfile at the current directory (if it is not already there) and adds all installed guards or the given GUARD into it'
- # Appends the Guard template to the `Guardfile`, or creates an initial
- # `Guardfile` when no Guard name is passed.
+ method_option :bare,
+ :type => :boolean,
+ :default => false,
+ :aliases => '-b',
+ :banner => 'Generate a bare Guardfile without adding any installed guard into it'
+
+ # Initializes the templates of all installed Guards and adds them
+ # to the `Guardfile` when no Guard name is passed. When passed
+ # a guard name is does the same but only for that Guard.
#
- # @see Guard.initialize_template
+ # @see Guard::Guard.initialize_template
+ # @see Guard::Guard.initialize_all_templates
#
# @param [String] guard_name the name of the Guard to initialize
#
def init(guard_name = nil)
verify_bundler_presence
- ::Guard.initialize_template(guard_name)
+
+ ::Guard.create_guardfile(:abort_on_existence => options[:bare])
+
+ return if options[:bare]
+
+ if guard_name.nil?
+ ::Guard::initialize_all_templates
+ else
+ ::Guard.initialize_template(guard_name)
+ end
end
desc 'show', 'Show all defined Guards and their options'
View
36 spec/guard/cli_spec.rb
@@ -138,13 +138,43 @@
end
describe '#init' do
- before { ::Guard.stub(:initialize_template) }
+ let(:options) { {:bare => false} }
- it 'delegates to Guard::DslDescriber.list' do
- ::Guard.should_receive(:initialize_template)
+ before do
+ subject.stub(:options => options)
+ ::Guard.stub(:create_guardfile)
+ ::Guard.stub(:initialize_all_templates)
+ end
+
+ it 'creates a Guardfile by delegating to Guard.create_guardfile' do
+ ::Guard.should_receive(:create_guardfile).with(:abort_on_existence => options[:bare])
+ subject.init
+ end
+
+ it 'initializes the templates of all installed Guards by delegating to Guard.initialize_all_templates' do
+ ::Guard.should_receive(:initialize_all_templates)
subject.init
end
+ context 'when passed a guard name' do
+ it 'initializes the template of the passed Guard by delegating to Guard.initialize_template' do
+ ::Guard.should_receive(:initialize_template).with('rspec')
+ subject.init 'rspec'
+ end
+ end
+
+ context 'with the bare option' do
+ let(:options) { {:bare => true} }
+
+ it 'Only creates the Guardfile and does not initialize any Guard template' do
+ ::Guard.should_receive(:create_guardfile)
+ ::Guard.should_not_receive(:initialize_template)
+ ::Guard.should_not_receive(:initialize_all_templates)
+
+ subject.init
+ end
+ end
+
context 'when running with Bundler' do
before do
@bundler_env = ENV['BUNDLE_GEMFILE']
View
118 spec/guard_spec.rb
@@ -7,76 +7,102 @@
File.exists?(Guard::GUARDFILE_TEMPLATE).should be_true
end
- describe ".initialize_template" do
+ describe ".create_guardfile" do
before { Dir.stub(:pwd).and_return "/home/user" }
- context "with a Guard name" do
- class Guard::Foo < Guard::Guard
+ context "with an existing Guardfile" do
+ before { File.should_receive(:exist?).and_return true }
+
+ it "does not copy the Guardfile template or notify the user" do
+ ::Guard::UI.should_not_receive(:info)
+ FileUtils.should_not_receive(:cp)
+
+ subject.create_guardfile
end
- context "with an existing Guardfile" do
- before { File.should_receive(:exist?).and_return true }
+ it "does not display any kind of error or abort" do
+ ::Guard::UI.should_not_receive(:error)
+ subject.should_not_receive(:abort)
+ subject.create_guardfile
+ end
- it "initializes the Guard" do
- Guard::Foo.should_receive(:init)
- Guard.initialize_template('foo')
+ context "with the :abort_on_existence option set to true" do
+ it "displays an error message and aborts the process" do
+ ::Guard::UI.should_receive(:error).with("Guardfile already exists at /home/user/Guardfile")
+ subject.should_receive(:abort)
+ subject.create_guardfile(:abort_on_existence => true)
end
end
+ end
- context "without an existing Guardfile" do
- before { File.should_receive(:exist?).and_return false }
+ context "without an existing Guardfile" do
+ before { File.should_receive(:exist?).and_return false }
- it "copies the Guardfile template and initializes the Guard" do
- ::Guard::UI.should_receive(:info).with("Writing new Guardfile to /home/user/Guardfile")
- FileUtils.should_receive(:cp).with(an_instance_of(String), 'Guardfile')
- Guard::Foo.should_receive(:init)
- Guard.initialize_template('foo')
- end
+ it "copies the Guardfile template and notifies the user" do
+ ::Guard::UI.should_receive(:info)
+ FileUtils.should_receive(:cp)
+
+ subject.create_guardfile
end
+ end
+ end
- context "with a user defined template" do
- let(:template) { File.join(Guard::HOME_TEMPLATES, '/bar') }
+ describe ".initialize_template" do
+ context 'with an installed Guard implementation' do
+ let(:foo_guard) { double('Guard::Foo').as_null_object }
- before {
- File.should_receive(:exist?).with('Guardfile').and_return false
- File.should_receive(:exist?).with(template).and_return true
- }
+ before { ::Guard.should_receive(:get_guard_class).and_return(foo_guard) }
- it "copies the Guardfile template and initializes the Guard" do
- FileUtils.should_receive(:cp).with(an_instance_of(String), 'Guardfile')
- File.should_receive(:read).with('Guardfile').and_return 'Guardfile content'
- File.should_receive(:read).with(template).and_return 'Template content'
- io = StringIO.new
- File.should_receive(:open).with('Guardfile', 'wb').and_yield io
- Guard.initialize_template('bar')
- io.string.should eql "Guardfile content\n\nTemplate content\n"
- end
+ it "initializes the Guard" do
+ foo_guard.should_receive(:init)
+ subject.initialize_template('foo')
end
end
- context "without a Guard name" do
- context "with an existing Guardfile" do
- before { File.should_receive(:exist?).and_return true }
+ context "with a user defined template" do
+ let(:template) { File.join(Guard::HOME_TEMPLATES, '/bar') }
- it "shows an error" do
- Guard.should_receive(:exit).with 1
- ::Guard::UI.should_receive(:error).with("Guardfile already exists at /home/user/Guardfile")
- Guard.initialize_template
- end
+ before { File.should_receive(:exist?).with(template).and_return true }
+
+ it "copies the Guardfile template and initializes the Guard" do
+ File.should_receive(:read).with('Guardfile').and_return 'Guardfile content'
+ File.should_receive(:read).with(template).and_return 'Template content'
+ io = StringIO.new
+ File.should_receive(:open).with('Guardfile', 'wb').and_yield io
+ subject.initialize_template('bar')
+ io.string.should eql "Guardfile content\n\nTemplate content\n"
end
+ end
- context "without an existing Guardfile" do
- before { File.should_receive(:exist?).and_return false }
+ context "when the passed guard can't be found" do
+ before do
+ ::Guard.should_receive(:get_guard_class).and_return nil
+ File.should_receive(:exist?).and_return false
+ end
- it "copies the Guardfile template" do
- ::Guard::UI.should_receive(:info).with("Writing new Guardfile to /home/user/Guardfile")
- FileUtils.should_receive(:cp).with(an_instance_of(String), 'Guardfile')
- Guard.initialize_template
- end
+ it "notifies the user about the problem" do
+ ::Guard::UI.should_receive(:error).with(
+ "Could not load 'guard/foo' or '~/.guard/templates/foo' or find class Guard::Foo"
+ )
+ subject.initialize_template('foo')
end
end
end
+ describe ".initialize_all_templates" do
+ let(:guards) { ['rspec', 'spork', 'phpunit'] }
+
+ before { subject.should_receive(:guard_gem_names).and_return(guards) }
+
+ it "calls Guard.initialize_template on all installed guards" do
+ guards.each do |g|
+ subject.should_receive(:initialize_template).with(g)
+ end
+
+ subject.initialize_all_templates
+ end
+ end
+
describe ".setup" do
subject { ::Guard.setup }
Please sign in to comment.
Something went wrong with that request. Please try again.