Felix Frank
all the Resource
classes hardly relate
Class |
Instance |
https://en.wikipedia.org/wiki/Otter#/media/File:Fischotter,_Lutra_Lutra.JPG |
https://en.wikipedia.org/wiki/Rooster#/media/File:El_Gallo_Ukraine.jpg |
Class |
Instance |
http://www.creationscience.com/onlinebook/LifeSciences13.html |
https://en.wikipedia.org/wiki/Otter#/media/File:Fischotter,_Lutra_Lutra.JPG |
Class String ... end
same as
String = Class.new do ... end
+---------+ +-...
| | |
BasicObject-----|-->(BasicObject)-------|-...
^ | ^ |
| | | |
Object---------|----->(Object)---------|-...
^ | ^ |
| | | |
+-------+ | +--------+ |
| | | | | |
| Module-|---------|--->(Module)-|-...
| ^ | | ^ |
| Class-|---------|---->(Class)-|-...
| ^ | | ^ |
| +---+ | +----+
obj--->OtherClass---------->(OtherClass)-----------...
http://ruby-doc.org/core-2.2.0/Class.html
http://theawesomedaily.com/21-things-that-look-exactly-like-donald-trump/
Puppet types take advantage of that
This code...
Puppet::Type.newtype(:cron) do
# code!
end
...effectively gives you:
class Puppet::Type::Cron : Puppet::Type do
# generated code!
end
manifest resources |
catalog resources |
Resource Abstraction Layer |
system entities |
file { '/etc/motd':
mode => 644
}
cron { 'break-all-the-things':
command => '/opt/scripts/cleanup.rb'
}
{
"type": "File",
"title": "/etc/motd",
"tags": ["file","class"],
"file": "/tmp/example-manifest.pp",
"line": 1,
"exported": false,
"parameters": {
"mode": 644
}
}
(resource abstraction layer)
-rw-r--r-- 1 root root 0 Feb 5 2011 /etc/motd
# HEADER: ...
# Puppet Name: break-all-the-things
1 1 2 * * /usr/scripts/cleanup.rb
http://www.theawl.com/2010/02/church-boring
So what about this
class Puppet::Type::Cron : Puppet::Type do
# generated code!
end
versus this
Puppet::Type
code,
def self.allattrs
def retrieve
class Puppet::Parameter
class <<self
# ...
def validate
# ...
end
end
end
Puppet::Parameter::validate
is a class method
Puppet::Type
newproperty(:user) do
newparam(:name) do
Things like self.newparam
or self.ensurable
self.instances
is pretty neat
http://devopsreactions.tumblr.com/post/129272206864/how-i-picture-the-thoughts-of-someone-saying-that
Parameters can never do that
Classic property: Is the content on disk?
install_options
Classic parameter: Unsyncable, since flags cannot be reset after the fact
{
"type": "Package",
"title": "cowsay",
"parameters": {
"ensure": "installed"
}
}
Package[cowsay]/ensure: present
Puppet::Provider::Package.prefetch
takes a hash argument
{ 'cowsay' => Package[cowsay] }
...where Package[cowsay]
is an instance
of Puppet::Type::Package
prefetch
in turn calls
Puppet::Provider::Package::Dpkg.instances
assuming Dpkg or Apt is the selected provider
the instances
hook produces
a list of Provider
instances
Type::Package.provider(:apt).new
or in other words
Provider::Package::Apt.new
lib/puppet/provider/parsedfile.rb
ParsedFile peculiarities
See Util::FileParsing
text_line :comment, :match => /^\s*#/
text_line :blank, :match => /^\s*$/
record_line :parsed,
:fields => %w{options type key name},
:optional => %w{options},
ParsedFile peculiarities
def self.prefetch_all_targets(resources)
records = []
targets(resources).each do |target|
records += prefetch_target(target)
end
records
end
ParsedFile peculiarities
def flush
# ...
self.class.flush(@property_hash)
end
ParsedFile peculiarities
flush
(true for some other providers as well)
def self.flush
@modified.each do |target|
flush_target(target)
end
end
ParsedFile peculiarities
def self.flush_target(target)
backup(target)
records = target_records(target)
target_object(target).write(to_file(records))
end
Look at augeas providers instead