[Pkg-puppet-devel] [SCM] Puppet packaging for Debian branch, experimental, updated. debian/2.6.8-1-844-g7ec39d5

Daniel Pittman daniel at puppetlabs.com
Tue May 10 08:18:48 UTC 2011


The following commit has been merged in the experimental branch:
commit 65b9a3c4f4e6830ed094d46381050dfa72c7eccd
Author: Daniel Pittman <daniel at puppetlabs.com>
Date:   Fri Apr 29 15:19:24 2011 -0700

    (#7221) Strip bad whitespace from face and action docs.
    
    We now strip whitespace in face (and related) documentation in two places:
    
    We strip any trailing whitespace on each line, just because.
    
    We strip any leading indent, but not all leading whitespace, from the text.
    That is, we strip the *minimum* amount of whitespace that we can take from
    every line in the documentation without changing the overall content.
    
    Reviewed-By: Pieter van de Bruggen <pieter at puppetlabs.com>

diff --git a/lib/puppet/interface/documentation.rb b/lib/puppet/interface/documentation.rb
index d0bfbb2..91db0e0 100644
--- a/lib/puppet/interface/documentation.rb
+++ b/lib/puppet/interface/documentation.rb
@@ -1,35 +1,74 @@
+# This isn't usable outside Puppet::Interface; don't load it alone.
 class Puppet::Interface
-  module TinyDocs
-    attr_accessor :summary
-    def summary(value = nil)
-      self.summary = value unless value.nil?
-      @summary
+  module DocGen
+    def self.strip_whitespace(text)
+      text.gsub!(/[ \t\f]+$/, '')
+
+      # We need to identify an indent: the minimum number of whitespace
+      # characters at the start of any line in the text.
+      indent = text.each_line.map {|x| x.index(/[^\s]/) }.compact.min
+
+      if indent > 0 then
+        text.gsub!(/^[ \t\f]{0,#{indent}}/, '')
+      end
+
+      return text
     end
-    def summary=(value)
-      value = value.to_s
-      value =~ /\n/ and
-        raise ArgumentError, "Face summary should be a single line; put the long text in 'description' instead."
 
-      @summary = value
+    # The documentation attributes all have some common behaviours; previously
+    # we open-coded them across the set of six things, but that seemed
+    # wasteful - especially given that they were literally the same, and had
+    # the same bug hidden in them.
+    #
+    # This feels a bit like overkill, but at least the common code is common
+    # now. --daniel 2011-04-29
+    def attr_doc(name, &validate)
+      # Now, which form of the setter do we want, validated or not?
+      get_arg = "value.to_s"
+      if validate
+        define_method(:"_validate_#{name}", validate)
+        get_arg = "_validate_#{name}(#{get_arg})"
+      end
+
+      # We use module_eval, which I don't like much, because we can't have an
+      # argument to a block with a default value in Ruby 1.8, and I don't like
+      # the side-effects (eg: no argument count validation) of using blocks
+      # without as metheds.  When we are 1.9 only (hah!) you can totally
+      # replace this with some up-and-up define_method. --daniel 2011-04-29
+      module_eval(<<-EOT, __FILE__, __LINE__ + 1)
+        def #{name}(value = nil)
+          self.#{name} = value unless value.nil?
+          @#{name}
+        end
+
+        def #{name}=(value)
+          @#{name} = Puppet::Interface::DocGen.strip_whitespace(#{get_arg})
+        end
+      EOT
     end
+  end
+
+  module TinyDocs
+    extend Puppet::Interface::DocGen
 
-    attr_accessor :description
-    def description(value = nil)
-      self.description = value unless value.nil?
-      @description
+    attr_doc :summary do |value|
+      value =~ /\n/ and
+        raise ArgumentError, "Face summary should be a single line; put the long text in 'description' instead."
+      value
     end
+
+    attr_doc :description
   end
 
   module FullDocs
+    extend Puppet::Interface::DocGen
     include TinyDocs
 
-    attr_accessor :examples
-    def examples(value = nil)
-      self.examples = value unless value.nil?
-      @examples
-    end
+    attr_doc :examples
+    attr_doc :notes
+    attr_doc :license
 
-    attr_accessor :short_description
+    attr_doc :short_description
     def short_description(value = nil)
       self.short_description = value unless value.nil?
       if @short_description.nil? then
@@ -50,37 +89,20 @@ class Puppet::Interface
         if value =~ /\n/ then
           raise ArgumentError, 'author should be a single line; use multiple statements for multiple authors'
         end
-        @authors.push(value)
+        @authors.push(Puppet::Interface::DocGen.strip_whitespace(value))
       end
       @authors.empty? ? nil : @authors.join("\n")
     end
-    def author=(value)
-      if Array(value).any? {|x| x =~ /\n/ } then
-        raise ArgumentError, 'author should be a single line; use multiple statements'
-      end
-      @authors = Array(value)
-    end
     def authors
       @authors
     end
-    def authors=(value)
+    def author=(value)
       if Array(value).any? {|x| x =~ /\n/ } then
         raise ArgumentError, 'author should be a single line; use multiple statements'
       end
-      @authors = Array(value)
-    end
-
-    attr_accessor :notes
-    def notes(value = nil)
-      @notes = value unless value.nil?
-      @notes
-    end
-
-    attr_accessor :license
-    def license(value = nil)
-      @license = value unless value.nil?
-      @license
+      @authors = Array(value).map{|x| Puppet::Interface::DocGen.strip_whitespace(x) }
     end
+    alias :authors= :author=
 
     def copyright(owner = nil, years = nil)
       if years.nil? and not owner.nil? then
diff --git a/spec/shared_behaviours/documentation_on_faces.rb b/spec/shared_behaviours/documentation_on_faces.rb
index dd2bd31..3cfb178 100644
--- a/spec/shared_behaviours/documentation_on_faces.rb
+++ b/spec/shared_behaviours/documentation_on_faces.rb
@@ -20,20 +20,59 @@ shared_examples_for "documentation on faces" do
     end
   end
 
-  # Should they accept multiple lines?
-  Attrs.each do |attr|
-    text = "with\nnewlines"
-
-    if SingleLineAttrs.include? attr then
-      it "should not accept multiline values for #{attr}" do
-        expect { subject.send("#{attr}=", text) }.
-          to raise_error ArgumentError, /#{attr} should be a single line/
-        subject.send(attr).should be_nil
-      end
-    else
-      it "should accept multiline values for #{attr}" do
-        expect { subject.send("#{attr}=", text) }.not_to raise_error
-        subject.send(attr).should == text
+  Attrs.each do |getter|
+    setter = "#{getter}=".to_sym
+    context "#{getter}" do
+      it "should strip leading whitespace on a single line" do
+        subject.send(setter, "  death to whitespace")
+        subject.send(getter).should == "death to whitespace"
+      end
+
+      it "should strip trailing whitespace on a single line" do
+        subject.send(setter, "death to whitespace  ")
+        subject.send(getter).should == "death to whitespace"
+      end
+
+      it "should strip whitespace at both ends at once" do
+        subject.send(setter, "  death to whitespace  ")
+        subject.send(getter).should == "death to whitespace"
+      end
+
+      multiline_text = "with\nnewlines"
+      if SingleLineAttrs.include? getter then
+        it "should not accept multiline values" do
+          expect { subject.send(setter, multiline_text) }.
+            to raise_error ArgumentError, /#{getter} should be a single line/
+          subject.send(getter).should be_nil
+        end
+      else
+        it "should accept multiline values" do
+          expect { subject.send(setter, multiline_text) }.not_to raise_error
+          subject.send(getter).should == multiline_text
+        end
+
+        [1, 2, 4, 7, 25].each do |length|
+          context "#{length} chars indent" do
+            indent = ' ' * length
+
+            it "should strip leading whitespace on multiple lines" do
+              text = "this\nis\the\final\outcome"
+              subject.send(setter, text.gsub(/^/, indent))
+              subject.send(getter).should == text
+            end
+
+            it "should not remove formatting whitespace, only global indent" do
+              text = "this\n  is\n    the\n  ultimate\ntest\n"
+              subject.send(setter, text.gsub(/^/, indent))
+              subject.send(getter).should == text
+            end
+          end
+        end
+
+        it "should strip whitespace with a blank line" do
+          subject.send(setter, "  this\n\n  should outdent\n")
+          subject.send(getter).should == "this\n\nshould outdent\n"
+        end
       end
     end
   end

-- 
Puppet packaging for Debian



More information about the Pkg-puppet-devel mailing list