Class: Kube::Schema::Resource

Inherits:
Object
  • Object
show all
Defined in:
lib/kube/schema/resource.rb

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(hash = {}, &block) ⇒ Resource

Returns a new instance of Resource.



7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
# File 'lib/kube/schema/resource.rb', line 7

def initialize(hash = {}, &block)
  deep_symbolize_keys(self.class.defaults.to_h).then do |defaults|

    # You are NEVER allowed to change `apiVersion` or `kind`
    # Therefore, they are ONLY ever set from the self.defaults
    # property.
    deep_symbolize_keys(hash).then do |symbolized|
      @data = defaults

      # This is extracting "top-level" properties from the input hash
      # such as [apiVersion, spec, metadata, roleRef, ...]
      # We then ignore the rest of the attributes by design.
      self.class.schema_properties.each do |property|
        if symbolized.key?(property)
          @data[property] = symbolized.delete(property)
        end
      end
    end
  end

  if block_given?
    @data.instance_exec(&block)
  end
end

Class Method Details

.defaultsObject

Gets overridden by the factory in Kube::Schema::Instance. Returns a frozen Hash like { “apiVersion” => “apps/v1”, “kind” => “Deployment” }



43
44
45
# File 'lib/kube/schema/resource.rb', line 43

def self.defaults
  raise "Kube::Schema::Resource should NOT be instanciated directly"
end

.schemaObject

Gets overridden by the factory in Kube::Schema::Instance



33
34
35
# File 'lib/kube/schema/resource.rb', line 33

def self.schema
  raise "Kube::Schema::Resource should NOT be instanciated directly"
end

.schema_propertiesObject



37
38
39
# File 'lib/kube/schema/resource.rb', line 37

def self.schema_properties
  raise "Kube::Schema::Resource should NOT be instanciated directly"
end

Instance Method Details

#==(other) ⇒ Object



100
101
102
# File 'lib/kube/schema/resource.rb', line 100

def ==(other)
  other.is_a?(Resource) && to_h == other.to_h
end

#to_hObject

Returns the resource data as a Hash. Defaults (apiVersion, kind) from the schema are authoritative and cannot be overridden – they are facts derived from the GVK metadata.



77
78
79
80
81
82
83
84
85
86
87
88
89
90
# File 'lib/kube/schema/resource.rb', line 77

def to_h
  defaults = self.class.defaults
  data = deep_compact(@data)
  data = data.reject { |_, v| v.is_a?(Hash) && v.empty? }

  if defaults
    symbolized = deep_symbolize_keys(defaults)
    # Defaults go first (for key ordering), then user data minus
    # any attempts to override the authoritative keys.
    symbolized.merge(data.reject { |k, _| symbolized.key?(k) })
  else
    data
  end
end

#to_yamlObject

Serializes to clean Kubernetes YAML. Raises Kube::ValidationError if the resource is not valid.



94
95
96
97
98
# File 'lib/kube/schema/resource.rb', line 94

def to_yaml
  if valid!
    deep_stringify_keys(to_h).to_yaml
  end
end

#valid!Object

Like #valid? but raises Kube::ValidationError with details on failure. The error message includes the resource kind and name for context.



57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
# File 'lib/kube/schema/resource.rb', line 57

def valid!
  if self.class.schema.nil?
    true
  else
    data = deep_stringify_keys(to_h)
    errors = self.class.schema.validate(data).to_a

    unless errors.empty?
      kind = self.class.defaults&.dig("kind")
      name = data.dig("metadata", "name")
      raise Kube::ValidationError.new(errors, kind: kind, name: name, manifest: data)
    end

    true
  end
end

#valid?Boolean

Returns:

  • (Boolean)


47
48
49
50
51
52
53
# File 'lib/kube/schema/resource.rb', line 47

def valid?
  if self.class.schema.nil?
    true
  else
    self.class.schema.valid?(deep_stringify_keys(to_h))
  end
end