1 | #
|
---|
2 | # range.rb
|
---|
3 | #
|
---|
4 |
|
---|
5 | # TODO(Krzysztof Wilczynski): We probably need to approach numeric values differently ...
|
---|
6 |
|
---|
7 | module Puppet::Parser::Functions
|
---|
8 | newfunction(:range, :type => :rvalue, :doc => <<-EOS
|
---|
9 | When given range in the form of (start, stop) it will extrapolate a range as
|
---|
10 | an array.
|
---|
11 |
|
---|
12 | *Examples:*
|
---|
13 |
|
---|
14 | range("0", "9")
|
---|
15 |
|
---|
16 | Will return: [0,1,2,3,4,5,6,7,8,9]
|
---|
17 |
|
---|
18 | range("00", "09")
|
---|
19 |
|
---|
20 | Will return: [0,1,2,3,4,5,6,7,8,9] (Zero padded strings are converted to
|
---|
21 | integers automatically)
|
---|
22 |
|
---|
23 | range("a", "c")
|
---|
24 |
|
---|
25 | Will return: ["a","b","c"]
|
---|
26 |
|
---|
27 | range("host01", "host10")
|
---|
28 | Will return: ["host01", "host02", ..., "host09", "host10"]
|
---|
29 | NB Be explicit in including trailing zeros. Otherwise the underlying ruby function will fail.
|
---|
30 |
|
---|
31 | Passing a third argument will cause the generated range to step by that
|
---|
32 | interval, e.g.
|
---|
33 |
|
---|
34 | range("0", "9", "2")
|
---|
35 |
|
---|
36 | Will return: [0,2,4,6,8]
|
---|
37 | EOS
|
---|
38 | ) do |arguments|
|
---|
39 |
|
---|
40 | raise(Puppet::ParseError, 'range(): Wrong number of ' +
|
---|
41 | 'arguments given (0 for 1)') if arguments.size == 0
|
---|
42 |
|
---|
43 | if arguments.size > 1
|
---|
44 | start = arguments[0]
|
---|
45 | stop = arguments[1]
|
---|
46 | step = arguments[2].nil? ? 1 : arguments[2].to_i.abs
|
---|
47 |
|
---|
48 | type = '..' # Use the simplest type of Range available in Ruby
|
---|
49 |
|
---|
50 | else # arguments.size == 1
|
---|
51 | value = arguments[0]
|
---|
52 |
|
---|
53 | if m = value.match(/^(\w+)(\.\.\.?|\-)(\w+)$/)
|
---|
54 | start = m[1]
|
---|
55 | stop = m[3]
|
---|
56 |
|
---|
57 | type = m[2]
|
---|
58 | step = 1
|
---|
59 | elsif value.match(/^.+$/)
|
---|
60 | raise(Puppet::ParseError, "range(): Unable to compute range " +
|
---|
61 | "from the value: #{value}")
|
---|
62 | else
|
---|
63 | raise(Puppet::ParseError, "range(): Unknown range format: #{value}")
|
---|
64 | end
|
---|
65 | end
|
---|
66 |
|
---|
67 | # If we were given an integer, ensure we work with one
|
---|
68 | if start.to_s.match(/^\d+$/)
|
---|
69 | start = start.to_i
|
---|
70 | stop = stop.to_i
|
---|
71 | else
|
---|
72 | start = start.to_s
|
---|
73 | stop = stop.to_s
|
---|
74 | end
|
---|
75 |
|
---|
76 | range = case type
|
---|
77 | when /^(\.\.|\-)$/ then (start .. stop)
|
---|
78 | when '...' then (start ... stop) # Exclusive of last element
|
---|
79 | end
|
---|
80 |
|
---|
81 | result = range.step(step).to_a
|
---|
82 |
|
---|
83 | return result
|
---|
84 | end
|
---|
85 | end
|
---|
86 |
|
---|
87 | # vim: set ts=2 sw=2 et :
|
---|