File: type_matchers.rb

package info (click to toggle)
ruby-rspec-puppet 4.0.2%2Bds-1
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 1,444 kB
  • sloc: ruby: 6,377; makefile: 6
file content (147 lines) | stat: -rw-r--r-- 3,849 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
# frozen_string_literal: true

module RSpec::Puppet
  module TypeMatchers
    class CreateGeneric
      def initialize(*_args)
        @exp_provider = nil
        @exp_parameters       = []
        @exp_properties       = []
        @exp_features         = []
        @exp_defaults         = {}
        @params_with_values   = {}
        @errors               = []
      end

      # specifies a provider to validate
      def with_provider(name)
        @exp_provider = name
        self
      end

      # ensures the listed properties are valid
      def with_properties(props)
        @exp_properties |= Array(props)
        self
      end

      # ensures the listed parameters are valid
      def with_parameters(params)
        @exp_parameters |= Array(params)
        self
      end

      # ensure the type has the list of features
      def with_features(features)
        @exp_features |= Array(features)
        self
      end

      #
      # ensures that the specified parameters with their values
      # results in a valid resource
      #
      def with_set_attributes(params)
        @params_with_values.merge!(params)
        self
      end

      def with_defaults(defaults_hash)
        @exp_defaults.merge!(defaults_hash)
        self
      end

      #
      # this is the method that drives all of the validation
      #
      def matches?(type_title_and_params)
        type   = type_title_and_params[0]
        title  = type_title_and_params[1]
        params = type_title_and_params[2]
        return false unless match_params(type) && match_props(type) && match_features(type)

        if @params_with_values != {} || @exp_provider
          # only build a resource if we are validating provider or setting
          # additional parameters
          resource = be_valid_resource(type, title, params.merge(@params_with_values))
          match_default_provider(resource) and match_default_values(resource)
        else
          true
        end
      end

      # checks that the specified params exist
      def match_params(type)
        match_attrs(type, @exp_parameters, :parameter)
      end

      # checks that the specified properties exist
      def match_props(type)
        match_attrs(type, @exp_properties, :property)
      end

      # checks that the specified features exist
      def match_features(type)
        match_attrs(type, @exp_features, :feature)
      end

      # builds the resource with the specified param values
      def be_valid_resource(type, title, params)
        params[:name] ||= title
        type.new(params)
      end

      #
      # checks that the expected provider is set
      #
      def match_default_provider(resource)
        return true unless @exp_provider
        return true if resource[:provider] == @exp_provider

        @errors.push("Expected provider: #{@exp_provider} does not match: #{resource[:provider]}")
        false
      end

      def match_default_values(_resource)
        # TODO: FINISH
        true
      end

      def description
        'be a valid type'
      end

      def failure_message
        "Not a valid type #{@errors.inspect}"
      end

      private

      def match_attrs(type, attrs, attr_type)
        baddies = []
        attrs.each do |param|
          param = param.to_sym
          if attr_type == :feature
            baddies.push(param) unless type.provider_feature(param)
          elsif !type.send(:"valid#{attr_type}?", param)
            baddies.push(param)
          end
        end
        if baddies.size.positive?
          @errors.push("Invalid #{pluralize(attr_type)}: #{baddies.join(',')}")
          false
        else
          true
        end
      end

      def pluralize(name)
        if name == :property
          'properties'
        else
          "#{name}s"
        end
      end
    end
  end
end