From 9e0256aabfd58dfce8cff65147722a844f56e006 Mon Sep 17 00:00:00 2001
From: Chris Price <chris@puppetlabs.com>
Date: Thu, 7 Jun 2012 09:09:14 -0700
Subject: Add support for a 'match' parameter to file_line

This commit adds a new parameter called "match"
to the file_line resource type, and support for
this new parameter to the corresponding ruby
provider.

This parameter is optional; file_line should work
just as before if you do not specify this parameter...
so this change should be backwards-compatible.

If you do specify the parameter, it is treated
as a regular expression that should be used when
looking through the file for a line.  This allows
you to do things like find a line that begins with
a certain prefix (e.g., "foo=.*"), and *replace*
the existing line with the line you specify in your
"line" parameter.  Without this capability, if you
already had a line "foo=bar" in your file and your
"line" parameter was set to "foo=baz", you'd end up
with *both* lines in the final file.  In many cases
this is undesirable.
---
 spec/unit/puppet/provider/file_line/ruby_spec.rb | 64 +++++++++++++++++++++++-
 spec/unit/puppet/type/file_line_spec.rb          | 24 +++++++++
 2 files changed, 86 insertions(+), 2 deletions(-)

(limited to 'spec')

diff --git a/spec/unit/puppet/provider/file_line/ruby_spec.rb b/spec/unit/puppet/provider/file_line/ruby_spec.rb
index b62e3a8..7857d39 100644
--- a/spec/unit/puppet/provider/file_line/ruby_spec.rb
+++ b/spec/unit/puppet/provider/file_line/ruby_spec.rb
@@ -2,8 +2,11 @@ require 'puppet'
 require 'tempfile'
 provider_class = Puppet::Type.type(:file_line).provider(:ruby)
 describe provider_class do
-  context "add" do
+  context "when adding" do
     before :each do
+      # TODO: these should be ported over to use the PuppetLabs spec_helper
+      #  file fixtures once the following pull request has been merged:
+      # https://github.com/puppetlabs/puppetlabs-stdlib/pull/73/files
       tmp = Tempfile.new('tmp')
       @tmpfile = tmp.path
       tmp.close!
@@ -30,8 +33,65 @@ describe provider_class do
     end
   end
 
-  context "remove" do
+  context "when matching" do
     before :each do
+      # TODO: these should be ported over to use the PuppetLabs spec_helper
+      #  file fixtures once the following pull request has been merged:
+      # https://github.com/puppetlabs/puppetlabs-stdlib/pull/73/files
+      tmp = Tempfile.new('tmp')
+      @tmpfile = tmp.path
+      tmp.close!
+      @resource = Puppet::Type::File_line.new(
+          {
+           :name => 'foo',
+           :path => @tmpfile,
+           :line => 'foo = bar',
+           :match => '^foo\s*=.*$',
+          }
+      )
+      @provider = provider_class.new(@resource)
+    end
+
+    it 'should raise an error if more than one line matches, and should not have modified the file' do
+      File.open(@tmpfile, 'w') do |fh|
+        fh.write("foo1\nfoo=blah\nfoo2\nfoo=baz")
+      end
+      @provider.exists?.should be_nil
+      expect { @provider.create }.to raise_error(Puppet::Error, /More than one line.*matches/)
+      File.read(@tmpfile).should eql("foo1\nfoo=blah\nfoo2\nfoo=baz")
+    end
+
+    it 'should replace a line that matches' do
+      File.open(@tmpfile, 'w') do |fh|
+        fh.write("foo1\nfoo=blah\nfoo2")
+      end
+      @provider.exists?.should be_nil
+      @provider.create
+      File.read(@tmpfile).chomp.should eql("foo1\nfoo = bar\nfoo2")
+    end
+    it 'should add a new line if no lines match' do
+      File.open(@tmpfile, 'w') do |fh|
+        fh.write("foo1\nfoo2")
+      end
+      @provider.exists?.should be_nil
+      @provider.create
+      File.read(@tmpfile).should eql("foo1\nfoo2\nfoo = bar\n")
+    end
+    it 'should do nothing if the exact line already exists' do
+      File.open(@tmpfile, 'w') do |fh|
+        fh.write("foo1\nfoo = bar\nfoo2")
+      end
+      @provider.exists?.should be_true
+      @provider.create
+      File.read(@tmpfile).chomp.should eql("foo1\nfoo = bar\nfoo2")
+    end
+  end
+
+  context "when removing" do
+    before :each do
+      # TODO: these should be ported over to use the PuppetLabs spec_helper
+      #  file fixtures once the following pull request has been merged:
+      # https://github.com/puppetlabs/puppetlabs-stdlib/pull/73/files
       tmp = Tempfile.new('tmp')
       @tmpfile = tmp.path
       tmp.close!
diff --git a/spec/unit/puppet/type/file_line_spec.rb b/spec/unit/puppet/type/file_line_spec.rb
index c86dbd2..e1c07ac 100644
--- a/spec/unit/puppet/type/file_line_spec.rb
+++ b/spec/unit/puppet/type/file_line_spec.rb
@@ -7,6 +7,30 @@ describe Puppet::Type.type(:file_line) do
   it 'should accept a line and path' do
     file_line[:line] = 'my_line'
     file_line[:line].should == 'my_line'
+    file_line[:path] = '/my/path'
+    file_line[:path].should == '/my/path'
+  end
+  it 'should accept a match regex' do
+    file_line[:match] = '^foo.*$'
+    file_line[:match].should == '^foo.*$'
+  end
+  it 'should not accept a match regex that does not match the specified line' do
+    expect {
+      Puppet::Type.type(:file_line).new(
+          :name   => 'foo',
+          :path   => '/my/path',
+          :line   => 'foo=bar',
+          :match  => '^bar=blah$'
+    )}.to raise_error(Puppet::Error, /the value must be a regex that matches/)
+  end
+  it 'should accept a match regex that does match the specified line' do
+    expect {
+      Puppet::Type.type(:file_line).new(
+          :name   => 'foo',
+          :path   => '/my/path',
+          :line   => 'foo=bar',
+          :match  => '^\s*foo=.*$'
+      )}.not_to raise_error
   end
   it 'should accept posix filenames' do
     file_line[:path] = '/tmp/path'
-- 
cgit v1.2.3