env:
matrix:
- PUPPET_GEM_VERSION="~> 2.7.0"
- - PUPPET_GEM_VERSION="~> 3.0.0"
- PUPPET_GEM_VERSION="~> 3.1.0"
- PUPPET_GEM_VERSION="~> 3.2.0"
+ - PUPPET_GEM_VERSION="~> 3.3.0"
+ - PUPPET_GEM_VERSION="~> 3.4.0"
global:
- PUBLISHER_LOGIN=puppetlabs
- secure: |-
env: PUPPET_GEM_VERSION="~> 2.7.0"
- rvm: 2.0.0
env: PUPPET_GEM_VERSION="~> 2.7.0"
- - rvm: 2.0.0
- env: PUPPET_GEM_VERSION="~> 3.0.0"
- rvm: 2.0.0
env: PUPPET_GEM_VERSION="~> 3.1.0"
- - rvm: 1.8.7
- env: PUPPET_GEM_VERSION="~> 3.2.0"
notifications:
email: false
group :development, :test do
gem 'rake', :require => false
+ gem 'pry', :require => false
gem 'rspec-puppet', :require => false
gem 'puppet-lint', :require => false
gem 'puppetlabs_spec_helper', :require => false
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
+
+
+Copyright 2014 Puppet Labs
+
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
Module Description
------------------
-APT automates obtaining and installing software packages on *nix systems.
+APT automates obtaining and installing software packages on \*nix systems.
Setup
-----
**What APT affects:**
-* package/service/configuration files for APT
+* package/service/configuration files for APT
* your system's `sources.list` file and `sources.list.d` directory
* NOTE: Setting the `purge_sources_list` and `purge_sources_list_d` parameters to 'true' will destroy any existing content that was not declared with Puppet. The default for these parameters is 'false'.
* system repositories
To begin using the APT module with default parameters, declare the class
include apt
-
-Puppet code that uses anything from the APT module requires that the core apt class be declared.
+
+Puppet code that uses anything from the APT module requires that the core apt class be declared/\s\+$//e
Usage
-----
-Using the APT module consists predominantly in declaring classes that provide desired functionality and features.
-
+Using the APT module consists predominantly in declaring classes that provide desired functionality and features.
+
### apt
`apt` provides a number of common resources and options that are shared by the various defined types in this module, so you MUST always include this class in your manifests.
update_timeout => undef
}
-Puppet will manage your system's `sources.list` file and `sources.list.d` directory but will do its best to respect existing content.
+Puppet will manage your system's `sources.list` file and `sources.list.d` directory but will do its best to respect existing content.
-If you declare your apt class with `purge_sources_list` and `purge_sources_list_d` set to 'true', Puppet will unapologetically purge any existing content it finds that wasn't declared with Puppet.
+If you declare your apt class with `purge_sources_list` and `purge_sources_list_d` set to 'true', Puppet will unapologetically purge any existing content it finds that wasn't declared with Puppet.
### apt::builddep
Forces a package to be installed from a specific release. This class is particularly useful when using repositories, like Debian, that are unstable in Ubuntu.
apt::force { 'glusterfs-server':
- release => 'unstable',
- version => '3.0.3',
- require => Apt::Source['debian_unstable'],
+ release => 'unstable',
+ version => '3.0.3',
+ require => Apt::Source['debian_unstable'],
}
### apt::key
key => '4BD6EC30',
key_server => 'pgp.mit.edu',
}
-
+
This resource creates an apt source named puppetlabs and gives Puppet information about the repository's location and key used to sign its packages. Puppet leverages Facter to determine the appropriate release, but you can set it directly by adding the release type.
Check your smoke test for syntax errors
info: /Stage[main]//Apt::Source[puppetlabs]/File[puppetlabs.list]: Scheduling refresh of Exec[puppetlabs apt update]
notice: /Stage[main]//Apt::Source[puppetlabs]/Exec[puppetlabs apt update]: Triggered 'refresh' from 1 events>
-The above example used a smoke test to easily lay out a resource declaration and apply it on your system. In production, you may want to declare your APT sources inside the classes where they’re needed.
+The above example used a smoke test to easily lay out a resource declaration and apply it on your system. In production, you may want to declare your APT sources inside the classes where they’re needed.
Implementation
--------------
Limitations
-----------
-This module should work across all versions of Debian/Ubuntu and support all major APT repository management features.
+This module should work across all versions of Debian/Ubuntu and support all major APT repository management features.
Development
------------
You can read the complete module contribution guide [on the Puppet Labs wiki.](http://projects.puppetlabs.com/projects/module-site/wiki/Module_contributing)
+License
+-------
+
+The original code for this module comes from Evolving Web and was licensed under the MIT license. Code added since the fork of this module is licensed under the Apache 2.0 License like the rest of the Puppet Labs products.
+
+The LICENSE contains both licenses.
+
Contributors
------------
* Ben Godfrey <ben.godfrey@wonga.com>
* Branan Purvine-Riley <branan@puppetlabs.com>
-* Christian G. Warden <cwarden@xerus.org>
-* Dan Bode <bodepd@gmail.com> <dan@puppetlabs.com>
-* Garrett Honeycutt <github@garretthoneycutt.com>
-* Jeff Wallace <jeff@evolvingweb.ca> <jeff@tjwallace.ca>
-* Ken Barber <ken@bob.sh>
-* Matthaus Litteken <matthaus@puppetlabs.com> <mlitteken@gmail.com>
-* Matthias Pigulla <mp@webfactory.de>
-* Monty Taylor <mordred@inaugust.com>
-* Peter Drake <pdrake@allplayers.com>
-* Reid Vandewiele <marut@cat.pdx.edu>
-* Robert Navarro <rnavarro@phiivo.com>
-* Ryan Coleman <ryan@puppetlabs.com>
-* Scott McLeod <scott.mcleod@theice.com>
-* Spencer Krum <spencer@puppetlabs.com>
-* William Van Hevelingen <blkperl@cat.pdx.edu> <wvan13@gmail.com>
-* Zach Leslie <zach@puppetlabs.com>
+* Christian G. Warden <cwarden@xerus.org>
+* Dan Bode <bodepd@gmail.com> <dan@puppetlabs.com>
+* Garrett Honeycutt <github@garretthoneycutt.com>
+* Jeff Wallace <jeff@evolvingweb.ca> <jeff@tjwallace.ca>
+* Ken Barber <ken@bob.sh>
+* Matthaus Litteken <matthaus@puppetlabs.com> <mlitteken@gmail.com>
+* Matthias Pigulla <mp@webfactory.de>
+* Monty Taylor <mordred@inaugust.com>
+* Peter Drake <pdrake@allplayers.com>
+* Reid Vandewiele <marut@cat.pdx.edu>
+* Robert Navarro <rnavarro@phiivo.com>
+* Ryan Coleman <ryan@puppetlabs.com>
+* Scott McLeod <scott.mcleod@theice.com>
+* Spencer Krum <spencer@puppetlabs.com>
+* William Van Hevelingen <blkperl@cat.pdx.edu> <wvan13@gmail.com>
+* Zach Leslie <zach@puppetlabs.com>
--- /dev/null
+require 'date'
+require 'open-uri'
+require 'net/ftp'
+require 'tempfile'
+
+if RUBY_VERSION == '1.8.7'
+ # Mothers cry, puppies die and Ruby 1.8.7's open-uri needs to be
+ # monkeypatched to support passing in :ftp_passive_mode.
+ require 'puppet_x/apt_key/patch_openuri'
+ OpenURI::Options.merge!({:ftp_active_mode => false,})
+end
+
+Puppet::Type.type(:apt_key).provide(:apt_key) do
+
+ KEY_LINE = {
+ :date => '[0-9]{4}-[0-9]{2}-[0-9]{2}',
+ :key_type => '(R|D)',
+ :key_size => '\d{4}',
+ :key_id => '[0-9a-fA-F]+',
+ :expires => 'expire(d|s)',
+ }
+
+ confine :osfamily => :debian
+ defaultfor :osfamily => :debian
+ commands :apt_key => 'apt-key'
+
+ def self.instances
+ key_array = apt_key('list').split("\n").collect do |line|
+ line_hash = key_line_hash(line)
+ next unless line_hash
+ expired = false
+
+ if line_hash[:key_expiry]
+ expired = Date.today > Date.parse(line_hash[:key_expiry])
+ end
+
+ new(
+ :name => line_hash[:key_id],
+ :id => line_hash[:key_id],
+ :ensure => :present,
+ :expired => expired,
+ :expiry => line_hash[:key_expiry],
+ :size => line_hash[:key_size],
+ :type => line_hash[:key_type] == 'R' ? :rsa : :dsa,
+ :created => line_hash[:key_created]
+ )
+ end
+ key_array.compact!
+ end
+
+ def self.prefetch(resources)
+ apt_keys = instances
+ resources.keys.each do |name|
+ if provider = apt_keys.find{ |key| key.name == name }
+ resources[name].provider = provider
+ end
+ end
+ end
+
+ def self.key_line_hash(line)
+ line_array = line.match(key_line_regexp).to_a
+ return nil if line_array.length < 5
+
+ return_hash = {
+ :key_id => line_array[3],
+ :key_size => line_array[1],
+ :key_type => line_array[2],
+ :key_created => line_array[4],
+ :key_expiry => nil,
+ }
+
+ return_hash[:key_expiry] = line_array[7] if line_array.length == 8
+ return return_hash
+ end
+
+ def self.key_line_regexp
+ # This regexp is trying to match the following output
+ # pub 4096R/4BD6EC30 2010-07-10 [expires: 2016-07-08]
+ # pub 1024D/CD2EFD2A 2009-12-15
+ regexp = /\A
+ pub # match only the public key, not signatures
+ \s+ # bunch of spaces after that
+ (#{KEY_LINE[:key_size]}) # size of the key, usually a multiple of 1024
+ #{KEY_LINE[:key_type]} # type of the key, usually R or D
+ \/ # separator between key_type and key_id
+ (#{KEY_LINE[:key_id]}) # hex id of the key
+ \s+ # bunch of spaces after that
+ (#{KEY_LINE[:date]}) # date the key was added to the keyring
+ # following an optional block which indicates if the key has an expiration
+ # date and if it has expired yet
+ (
+ \s+ # again with thes paces
+ \[ # we open with a square bracket
+ #{KEY_LINE[:expires]} # expires or expired
+ \: # a colon
+ \s+ # more spaces
+ (#{KEY_LINE[:date]}) # date indicating key expiry
+ \] # we close with a square bracket
+ )? # end of the optional block
+ \Z/x
+ regexp
+ end
+
+ def source_to_file(value)
+ if URI::parse(value).scheme.nil?
+ fail("The file #{value} does not exist") unless File.exists?(value)
+ value
+ else
+ begin
+ key = open(value, :ftp_active_mode => false).read
+ rescue OpenURI::HTTPError, Net::FTPPermError => e
+ fail("#{e.message} for #{resource[:source]}")
+ rescue SocketError
+ fail("could not resolve #{resource[:source]}")
+ else
+ tempfile(key)
+ end
+ end
+ end
+
+ def tempfile(content)
+ file = Tempfile.new('apt_key')
+ file.write content
+ file.close
+ file.path
+ end
+
+ def exists?
+ @property_hash[:ensure] == :present
+ end
+
+ def create
+ command = []
+ if resource[:source].nil? and resource[:content].nil?
+ # Breaking up the command like this is needed because it blows up
+ # if --recv-keys isn't the last argument.
+ command.push('adv', '--keyserver', resource[:server])
+ unless resource[:keyserver_options].nil?
+ command.push('--keyserver-options', resource[:keyserver_options])
+ end
+ command.push('--recv-keys', resource[:id])
+ elsif resource[:content]
+ command.push('add', tempfile(resource[:content]))
+ elsif resource[:source]
+ command.push('add', source_to_file(resource[:source]))
+ # In case we really screwed up, better safe than sorry.
+ else
+ fail("an unexpected condition occurred while trying to add the key: #{resource[:id]}")
+ end
+ apt_key(command)
+ @property_hash[:ensure] = :present
+ end
+
+ def destroy
+ apt_key('del', resource[:id])
+ @property_hash.clear
+ end
+
+ def read_only(value)
+ fail('This is a read-only property.')
+ end
+
+ mk_resource_methods
+
+ # Needed until PUP-1470 is fixed and we can drop support for Puppet versions
+ # before that.
+ def expired
+ @property_hash[:expired]
+ end
+
+ # Alias the setters of read-only properties
+ # to the read_only function.
+ alias :created= :read_only
+ alias :expired= :read_only
+ alias :expiry= :read_only
+ alias :size= :read_only
+ alias :type= :read_only
+end
--- /dev/null
+require 'pathname'
+
+Puppet::Type.newtype(:apt_key) do
+
+ @doc = <<-EOS
+ This type provides Puppet with the capabilities to manage GPG keys needed
+ by apt to perform package validation. Apt has it's own GPG keyring that can
+ be manipulated through the `apt-key` command.
+
+ apt_key { '4BD6EC30':
+ source => 'http://apt.puppetlabs.com/pubkey.gpg'
+ }
+
+ **Autorequires**:
+
+ If Puppet is given the location of a key file which looks like an absolute
+ path this type will autorequire that file.
+ EOS
+
+ ensurable
+
+ validate do
+ if self[:content] and self[:source]
+ fail('The properties content and source are mutually exclusive.')
+ end
+ end
+
+ newparam(:id, :namevar => true) do
+ desc 'The ID of the key you want to manage.'
+ # GPG key ID's should be either 32-bit (short) or 64-bit (long) key ID's
+ # and may start with the optional 0x
+ newvalues(/\A(0x)?[0-9a-fA-F]{8}\Z/, /\A(0x)?[0-9a-fA-F]{16}\Z/)
+ munge do |value|
+ if value.start_with?('0x')
+ id = value.partition('0x').last.upcase
+ else
+ id = value.upcase
+ end
+ if id.length == 16
+ id[8..-1]
+ else
+ id
+ end
+ end
+ end
+
+ newparam(:content) do
+ desc 'The content of, or string representing, a GPG key.'
+ end
+
+ newparam(:source) do
+ desc 'Location of a GPG key file, /path/to/file, ftp://, http:// or https://'
+ newvalues(/\Ahttps?:\/\//, /\Aftp:\/\//, /\A\/\w+/)
+ end
+
+ autorequire(:file) do
+ if self[:source] and Pathname.new(self[:source]).absolute?
+ self[:source]
+ end
+ end
+
+ newparam(:server) do
+ desc 'The key server to fetch the key from based on the ID.'
+ defaultto :'keyserver.ubuntu.com'
+ # Need to validate this, preferably through stdlib is_fqdn
+ # but still working on getting to that.
+ end
+
+ newparam(:keyserver_options) do
+ desc 'Additional options to pass to apt-key\'s --keyserver-options.'
+ end
+
+ newproperty(:expired) do
+ desc <<-EOS
+ Indicates if the key has expired.
+
+ This property is read-only.
+ EOS
+ end
+
+ newproperty(:expiry) do
+ desc <<-EOS
+ The date the key will expire, or nil if it has no expiry date.
+
+ This property is read-only.
+ EOS
+ end
+
+ newproperty(:size) do
+ desc <<-EOS
+ The key size, usually a multiple of 1024.
+
+ This property is read-only.
+ EOS
+ end
+
+ newproperty(:type) do
+ desc <<-EOS
+ The key type, either RSA or DSA.
+
+ This property is read-only.
+ EOS
+ end
+
+ newproperty(:created) do
+ desc <<-EOS
+ Date the key was created.
+
+ This property is read-only.
+ EOS
+ end
+end
--- /dev/null
+require 'uri'
+require 'stringio'
+require 'time'
+
+module URI
+ class FTP
+ def buffer_open(buf, proxy, options) # :nodoc:
+ if proxy
+ OpenURI.open_http(buf, self, proxy, options)
+ return
+ end
+ require 'net/ftp'
+
+ directories = self.path.split(%r{/}, -1)
+ directories.shift if directories[0] == '' # strip a field before leading slash
+ directories.each {|d|
+ d.gsub!(/%([0-9A-Fa-f][0-9A-Fa-f])/) { [$1].pack("H2") }
+ }
+ unless filename = directories.pop
+ raise ArgumentError, "no filename: #{self.inspect}"
+ end
+ directories.each {|d|
+ if /[\r\n]/ =~ d
+ raise ArgumentError, "invalid directory: #{d.inspect}"
+ end
+ }
+ if /[\r\n]/ =~ filename
+ raise ArgumentError, "invalid filename: #{filename.inspect}"
+ end
+ typecode = self.typecode
+ if typecode && /\A[aid]\z/ !~ typecode
+ raise ArgumentError, "invalid typecode: #{typecode.inspect}"
+ end
+
+ # The access sequence is defined by RFC 1738
+ ftp = Net::FTP.open(self.host)
+ ftp.passive = true if !options[:ftp_active_mode]
+ # todo: extract user/passwd from .netrc.
+ user = 'anonymous'
+ passwd = nil
+ user, passwd = self.userinfo.split(/:/) if self.userinfo
+ ftp.login(user, passwd)
+ directories.each {|cwd|
+ ftp.voidcmd("CWD #{cwd}")
+ }
+ if typecode
+ # xxx: typecode D is not handled.
+ ftp.voidcmd("TYPE #{typecode.upcase}")
+ end
+ if options[:content_length_proc]
+ options[:content_length_proc].call(ftp.size(filename))
+ end
+ ftp.retrbinary("RETR #{filename}", 4096) { |str|
+ buf << str
+ options[:progress_proc].call(buf.size) if options[:progress_proc]
+ }
+ ftp.close
+ buf.io.rewind
+ end
+
+ include OpenURI::OpenRead
+ end
+end
class apt(
$always_apt_update = false,
$disable_keys = undef,
- $proxy_host = false,
+ $proxy_host = undef,
$proxy_port = '8080',
$purge_sources_list = false,
$purge_sources_list_d = false,
+ $purge_preferences = false,
$purge_preferences_d = false,
$update_timeout = undef
) {
include apt::params
include apt::update
- validate_bool($purge_sources_list, $purge_sources_list_d, $purge_preferences_d)
+ validate_bool($purge_sources_list, $purge_sources_list_d,
+ $purge_preferences, $purge_preferences_d)
$sources_list_content = $purge_sources_list ? {
false => undef,
true => "# Repos managed by puppet.\n",
}
+ $preferences_content = $purge_preferences ? {
+ false => undef,
+ true => "Explanation: Preferences managed by Puppet\n
+Explanation: We need a bogus package line because of Debian Bug #732746\n
+Package: bogus-package\n",
+ }
+
if $always_apt_update == true {
Exec <| title=='apt_update' |> {
refreshonly => false,
notify => Exec['apt_update'],
}
+ file { 'apt-preferences':
+ ensure => present,
+ path => "${root}/preferences",
+ owner => root,
+ group => root,
+ mode => '0644',
+ content => $preferences_content,
+ }
+
file { 'preferences.d':
ensure => directory,
path => $preferences_d,
}
$proxy_set = $proxy_host ? {
- false => absent,
+ undef => absent,
default => present
}
}
'ubuntu': {
case $::lsbdistcodename {
- 'hardy','lucid','maverick','natty','oneiric','precise': {
+ 'hardy','maverick','natty','oneiric','precise': {
$backports_location = 'http://us.archive.ubuntu.com/ubuntu'
+ $ppa_options = '-y'
+ }
+ 'lucid': {
+ $backports_location = 'http://us.archive.ubuntu.com/ubuntu'
+ $ppa_options = undef
}
default: {
$backports_location = 'http://old-releases.ubuntu.com/ubuntu'
+ $ppa_options = '-y'
}
}
}
+ default: {
+ fail("Unsupported osfamily (${::osfamily}) or lsbdistid (${::lsbdistid})")
+ }
}
}
define apt::ppa(
$ensure = 'present',
$release = $::lsbdistcodename,
- $options = '-y'
+ $options = $apt::params::ppa_options,
) {
include apt::params
include apt::update
file { "${sources_list_d}/${sources_list_d_filename}":
ensure => 'absent',
+ mode => '0644',
+ owner => 'root',
+ gruop => 'root',
notify => Exec['apt_update'],
}
}
$download_delta = "0",
$verbose = "0",
) {
+ include apt::params
validate_bool(
$auto_fix,
require 'spec_helper_acceptance'
-describe 'apt::builddep' do
+describe 'apt::builddep', :unless => UNSUPPORTED_PLATFORMS.include?(fact('osfamily')) do
context 'reset' do
it 'removes packages' do
- shell('apt-get -y remove glusterfs-server')
+ shell('apt-get -y remove znc')
shell('apt-get -y remove g++')
end
end
it 'should work with no errors' do
pp = <<-EOS
include '::apt'
- apt::builddep { 'glusterfs-server': }
+ apt::builddep { 'znc': }
EOS
apply_manifest(pp, :catch_failures => true)
context 'reset' do
it 'removes packages' do
- shell('apt-get -y remove glusterfs-server')
+ shell('apt-get -y remove znc')
shell('apt-get -y remove g++')
end
end
--- /dev/null
+require 'spec_helper_acceptance'
+
+PUPPETLABS_GPG_KEY_ID = '4BD6EC30'
+PUPPETLABS_APT_URL = 'apt.puppetlabs.com'
+PUPPETLABS_GPG_KEY_FILE = 'pubkey.gpg'
+CENTOS_GPG_KEY_ID = 'C105B9DE'
+CENTOS_REPO_URL = 'ftp.cvut.cz/centos'
+CENTOS_GPG_KEY_FILE = 'RPM-GPG-KEY-CentOS-6'
+
+describe 'apt_key' do
+ before(:each) do
+ shell("apt-key del #{PUPPETLABS_GPG_KEY_ID}",
+ :acceptable_exit_codes => [0,1,2])
+ end
+
+ describe 'default options' do
+ key_versions = {
+ '32bit key id' => '4BD6EC30',
+ '64bit key id' => '1054B7A24BD6EC30',
+ '32bit lowercase key id' => '4bd6ec30',
+ '64bit lowercase key id' => '1054b7a24bd6ec30',
+ '0x formatted 32bit key id' => '0x4BD6EC30',
+ '0x formatted 64bit key id' => '0x1054B7A24BD6EC30',
+ '0x formatted 32bit lowercase key id' => '0x4bd6ec30',
+ '0x formatted 64bit lowercase key id' => '0x1054b7a24bd6ec30',
+ }
+
+ key_versions.each do |key, value|
+ context "#{key}" do
+ it 'works' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{value}',
+ ensure => 'present',
+ }
+ EOS
+
+ apply_manifest(pp, :catch_failures => true)
+ expect(apply_manifest(pp, :catch_failures => true).exit_code).to be_zero
+ shell("apt-key list | grep #{PUPPETLABS_GPG_KEY_ID}")
+ end
+ end
+ end
+
+ context 'invalid length key id' do
+ it 'fails' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '4B7A24BD6EC30',
+ }
+ EOS
+
+ apply_manifest(pp, :expect_failures => true) do |r|
+ expect(r.stderr).to match(/Valid values match/)
+ end
+ end
+ end
+ end
+
+ describe 'ensure =>' do
+ context 'absent' do
+ it 'is removed' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'absent',
+ }
+ EOS
+
+ # Install the key first
+ shell("apt-key adv --keyserver keyserver.ubuntu.com \
+ --recv-keys #{PUPPETLABS_GPG_KEY_ID}")
+ shell("apt-key list | grep #{PUPPETLABS_GPG_KEY_ID}")
+
+ # Time to remove it using Puppet
+ apply_manifest(pp, :catch_failures => true)
+ expect(apply_manifest(pp, :catch_failures => true).exit_code).to be_zero
+
+ shell("apt-key list | grep #{PUPPETLABS_GPG_KEY_ID}",
+ :acceptable_exit_codes => [1])
+ end
+ end
+ end
+
+ describe 'content =>' do
+ context 'puppetlabs gpg key' do
+ it 'works' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'present',
+ content => "-----BEGIN PGP PUBLIC KEY BLOCK-----
+Version: GnuPG v1.4.12 (GNU/Linux)
+Comment: GPGTools - http://gpgtools.org
+
+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
+=a34C
+-----END PGP PUBLIC KEY BLOCK-----",
+ }
+ EOS
+
+ apply_manifest(pp, :catch_failures => true)
+ expect(apply_manifest(pp, :catch_failures => true).exit_code).to be_zero
+ shell("apt-key list | grep #{PUPPETLABS_GPG_KEY_ID}")
+ end
+ end
+
+ context 'bogus key' do
+ it 'fails' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'present',
+ content => 'For posterity: such content, much bogus, wow',
+ }
+ EOS
+
+ apply_manifest(pp, :expect_failures => true) do |r|
+ expect(r.stderr).to match(/no valid OpenPGP data found/)
+ end
+ end
+ end
+ end
+
+ describe 'server =>' do
+ context 'pgp.mit.edu' do
+ it 'works' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'present',
+ server => 'pgp.mit.edu',
+ }
+ EOS
+
+ apply_manifest(pp, :catch_failures => true)
+ expect(apply_manifest(pp, :catch_failures => true).exit_code).to be_zero
+ shell("apt-key list | grep #{PUPPETLABS_GPG_KEY_ID}")
+ end
+ end
+
+ context 'nonexistant.key.server' do
+ it 'fails' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'present',
+ server => 'nonexistant.key.server',
+ }
+ EOS
+
+ apply_manifest(pp, :expect_failures => true) do |r|
+ expect(r.stderr).to match(/Host not found/)
+ end
+ end
+ end
+ end
+
+ describe 'source =>' do
+ context 'http://' do
+ it 'works' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'present',
+ source => 'http://#{PUPPETLABS_APT_URL}/#{PUPPETLABS_GPG_KEY_FILE}',
+ }
+ EOS
+
+ apply_manifest(pp, :catch_failures => true)
+ expect(apply_manifest(pp, :catch_failures => true).exit_code).to be_zero
+ shell("apt-key list | grep #{PUPPETLABS_GPG_KEY_ID}")
+ end
+
+ it 'fails with a 404' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'present',
+ source => 'http://#{PUPPETLABS_APT_URL}/herpderp.gpg',
+ }
+ EOS
+
+ apply_manifest(pp, :expect_failures => true) do |r|
+ expect(r.stderr).to match(/404 Not Found/)
+ end
+ end
+
+ it 'fails with a socket error' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'present',
+ source => 'http://apt.puppetlabss.com/herpderp.gpg',
+ }
+ EOS
+
+ apply_manifest(pp, :expect_failures => true) do |r|
+ expect(r.stderr).to match(/could not resolve/)
+ end
+ end
+ end
+
+ context 'ftp://' do
+ before(:each) do
+ shell("apt-key del #{CENTOS_GPG_KEY_ID}",
+ :acceptable_exit_codes => [0,1,2])
+ end
+
+ it 'works' do
+ pp = <<-EOS
+ apt_key { 'CentOS 6':
+ id => '#{CENTOS_GPG_KEY_ID}',
+ ensure => 'present',
+ source => 'ftp://#{CENTOS_REPO_URL}/#{CENTOS_GPG_KEY_FILE}',
+ }
+ EOS
+
+ apply_manifest(pp, :catch_failures => true)
+ expect(apply_manifest(pp, :catch_failures => true).exit_code).to be_zero
+ shell("apt-key list | grep #{CENTOS_GPG_KEY_ID}")
+ end
+
+ it 'fails with a 550' do
+ pp = <<-EOS
+ apt_key { 'CentOS 6':
+ id => '#{CENTOS_GPG_KEY_ID}',
+ ensure => 'present',
+ source => 'ftp://#{CENTOS_REPO_URL}/herpderp.gpg',
+ }
+ EOS
+
+ apply_manifest(pp, :expect_failures => true) do |r|
+ expect(r.stderr).to match(/550 Failed to open/)
+ end
+ end
+
+ it 'fails with a socket error' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'present',
+ source => 'ftp://apt.puppetlabss.com/herpderp.gpg',
+ }
+ EOS
+
+ apply_manifest(pp, :expect_failures => true) do |r|
+ expect(r.stderr).to match(/could not resolve/)
+ end
+ end
+ end
+
+ context 'https://' do
+ it 'works' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'present',
+ source => 'https://#{PUPPETLABS_APT_URL}/#{PUPPETLABS_GPG_KEY_FILE}',
+ }
+ EOS
+
+ apply_manifest(pp, :catch_failures => true)
+ expect(apply_manifest(pp, :catch_failures => true).exit_code).to be_zero
+ shell("apt-key list | grep #{PUPPETLABS_GPG_KEY_ID}")
+ end
+
+ it 'fails with a 404' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '4BD6EC30',
+ ensure => 'present',
+ source => 'https://#{PUPPETLABS_APT_URL}/herpderp.gpg',
+ }
+ EOS
+
+ apply_manifest(pp, :expect_failures => true) do |r|
+ expect(r.stderr).to match(/404 Not Found/)
+ end
+ end
+
+ it 'fails with a socket error' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '4BD6EC30',
+ ensure => 'present',
+ source => 'https://apt.puppetlabss.com/herpderp.gpg',
+ }
+ EOS
+
+ apply_manifest(pp, :expect_failures => true) do |r|
+ expect(r.stderr).to match(/could not resolve/)
+ end
+ end
+ end
+
+ context '/path/that/exists' do
+ before(:each) do
+ shell("curl -o /tmp/puppetlabs-pubkey.gpg \
+ http://#{PUPPETLABS_APT_URL}/#{PUPPETLABS_GPG_KEY_FILE}")
+ end
+
+ after(:each) do
+ shell('rm /tmp/puppetlabs-pubkey.gpg')
+ end
+
+ it 'works' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '4BD6EC30',
+ ensure => 'present',
+ source => '/tmp/puppetlabs-pubkey.gpg',
+ }
+ EOS
+
+ apply_manifest(pp, :catch_failures => true)
+ expect(apply_manifest(pp, :catch_failures => true).exit_code).to be_zero
+ shell("apt-key list | grep #{PUPPETLABS_GPG_KEY_ID}")
+ end
+ end
+
+ context '/path/that/does/not/exist' do
+ it 'fails' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'present',
+ source => '/tmp/totally_bogus.file',
+ }
+ EOS
+
+ apply_manifest(pp, :expect_failures => true) do |r|
+ expect(r.stderr).to match(/does not exist/)
+ end
+ end
+ end
+
+ context '/path/that/exists/with/bogus/content' do
+ before(:each) do
+ shell('echo "here be dragons" > /tmp/fake-key.gpg')
+ end
+
+ after(:each) do
+ shell('rm /tmp/fake-key.gpg')
+ end
+ it 'fails' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'present',
+ source => '/tmp/fake-key.gpg',
+ }
+ EOS
+
+ apply_manifest(pp, :expect_failures => true) do |r|
+ expect(r.stderr).to match(/no valid OpenPGP data found/)
+ end
+ end
+ end
+ end
+
+ describe 'keyserver_options =>' do
+ context 'debug' do
+ it 'works' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'present',
+ keyserver_options => 'debug',
+ }
+ EOS
+
+ apply_manifest(pp, :catch_failures => true)
+ expect(apply_manifest(pp, :catch_failures => true).exit_code).to be_zero
+ shell("apt-key list | grep #{PUPPETLABS_GPG_KEY_ID}")
+ end
+
+ it 'fails on invalid options' do
+ pp = <<-EOS
+ apt_key { 'puppetlabs':
+ id => '#{PUPPETLABS_GPG_KEY_ID}',
+ ensure => 'present',
+ keyserver_options => 'this is totally bonkers',
+ }
+ EOS
+
+ apply_manifest(pp, :expect_failures => true) do |r|
+ expect(r.stderr).to match(/--keyserver-options this is totally/)
+ end
+ end
+ end
+ end
+end
require 'spec_helper_acceptance'
-describe 'apt::key' do
+describe 'apt::key', :unless => UNSUPPORTED_PLATFORMS.include?(fact('osfamily')) do
context 'apt::key' do
it 'should work with no errors' do
pp = <<-EOS
require 'spec_helper_acceptance'
if fact('operatingsystem') == 'Ubuntu'
- describe 'apt::ppa' do
+ describe 'apt::ppa', :unless => UNSUPPORTED_PLATFORMS.include?(fact('osfamily')) do
context 'reset' do
it 'removes ppa' do
end
end
- context 'readding a removed ppa.' do
+ context 'reading a removed ppa.' do
it 'setup' do
- shell('add-apt-repository -y ppa:raravena80/collectd5')
# This leaves a blank file
- shell('add-apt-repository --remove ppa:raravena80/collectd5')
+ shell('echo > /etc/apt/sources.list.d/raravena80-collectd5-$(lsb_release -c -s).list')
end
- it 'should readd it successfully' do
+ it 'should read it successfully' do
pp = <<-EOS
include '::apt'
apt::ppa { 'ppa:raravena80/collectd5': }
end
context 'options' do
- context '-y' do
+ context '-y', :unless => default[:platform].match(/10\.04/) do
it 'works without failure' do
pp = <<-EOS
include '::apt'
context 'reset' do
it { shell('rm -rf /etc/apt/sources.list.d/canonical-kernel-team-ppa*', :acceptable_exit_codes => [0,1,2]) }
end
-
end
end
require 'spec_helper_acceptance'
-describe 'apt::source' do
+describe 'apt::source', :unless => UNSUPPORTED_PLATFORMS.include?(fact('osfamily')) do
context 'apt::source' do
context 'ensure => present' do
require 'spec_helper_acceptance'
-describe 'apt class' do
+describe 'apt class', :unless => UNSUPPORTED_PLATFORMS.include?(fact('osfamily')) do
context 'reset' do
it 'fixes the sources.list' do
end
end
+ context 'purge_preferences' do
+ context 'false' do
+ it 'creates a preferences file' do
+ shell("echo 'original' > /etc/apt/preferences")
+ end
+
+ it 'should work with no errors' do
+ pp = <<-EOS
+ class { 'apt': purge_preferences => false }
+ EOS
+
+ apply_manifest(pp, :catch_failures => true)
+ end
+
+ describe file('/etc/apt/preferences') do
+ it { should be_file }
+ it 'is not managed by Puppet' do
+ shell("grep 'original' /etc/apt/preferences", {:acceptable_exit_codes => 0})
+ end
+ end
+ end
+
+ context 'true' do
+ it 'creates a preferences file' do
+ shell('touch /etc/apt/preferences')
+ end
+
+ it 'should work with no errors' do
+ pp = <<-EOS
+ class { 'apt': purge_preferences => true }
+ EOS
+
+ apply_manifest(pp, :catch_failures => true)
+ end
+
+ describe file('/etc/apt/preferences') do
+ it { should be_file }
+ it 'is managed by Puppet' do
+ shell("grep 'Explanation' /etc/apt/preferences", {:acceptable_exit_codes => 0})
+ end
+ end
+ end
+ end
+
context 'purge_preferences_d' do
context 'false' do
it 'creates a preferences file' do
repos = 'main contrib non-free'
end
-describe 'apt::backports class' do
+describe 'apt::backports class', :unless => UNSUPPORTED_PLATFORMS.include?(fact('osfamily')) do
context 'defaults' do
it 'should work with no errors' do
pp = <<-EOS
require 'spec_helper_acceptance'
-describe 'apt class' do
+describe 'apt class', :unless => UNSUPPORTED_PLATFORMS.include?(fact('osfamily')) do
context 'default parameters' do
# Using puppet_apply as a helper
require 'spec_helper_acceptance'
-describe 'apt::conf define' do
+describe 'apt::conf define', :unless => UNSUPPORTED_PLATFORMS.include?(fact('osfamily')) do
context 'defaults' do
it 'should work with no errors' do
pp = <<-EOS
codename = fact('lsbdistcodename')
-describe 'apt::force define' do
+describe 'apt::force define', :unless => UNSUPPORTED_PLATFORMS.include?(fact('osfamily')) do
context 'defaults' do
it 'should work with no errors' do
pp = <<-EOS
--- /dev/null
+HOSTS:
+ ubuntu-server-10044-x64:
+ roles:
+ - master
+ platform: ubuntu-10.04-amd64
+ box : ubuntu-server-10044-x64-vbox4210-nocm
+ box_url : http://puppet-vagrant-boxes.puppetlabs.com/ubuntu-server-10044-x64-vbox4210-nocm.box
+ hypervisor : vagrant
+CONFIG:
+ log_level: debug
+ type: git
require 'spec_helper_acceptance'
-describe 'apt::pin define' do
+describe 'apt::pin define', :unless => UNSUPPORTED_PLATFORMS.include?(fact('osfamily')) do
context 'defaults' do
it 'should work with no errors' do
pp = <<-EOS
require 'spec_helper_acceptance'
-describe 'apt::release class' do
+describe 'apt::release class', :unless => UNSUPPORTED_PLATFORMS.include?(fact('osfamily')) do
context 'release_id' do
it 'should work with no errors' do
pp = <<-EOS
require 'spec_helper_acceptance'
-describe 'apt::unattended_upgrades class' do
+describe 'apt::unattended_upgrades class', :unless => UNSUPPORTED_PLATFORMS.include?(fact('osfamily')) do
context 'defaults' do
it 'should work with no errors' do
pp = <<-EOS
--- /dev/null
+require 'spec_helper_acceptance'
+
+describe 'unsupported distributions and OSes', :if => UNSUPPORTED_PLATFORMS.include?(fact('osfamily')) do
+ it 'class apt fails' do
+ pp = <<-EOS
+ class { 'apt': }
+ EOS
+ expect(apply_manifest(pp, :expect_failures => true).stderr).to match(/unsupported/i)
+ end
+end
require 'spec_helper'
describe 'apt', :type => :class do
+ let(:facts) { { :lsbdistid => 'Debian' } }
let :default_params do
{
:disable_keys => :undef,
:purge_sources_list => true,
:purge_sources_list_d => true,
},
+ {
+ :purge_preferences => true,
+ :purge_preferences_d => true,
+ },
{
:disable_keys => false
}
})
end
}
+ it {
+ if param_hash[:purge_preferences]
+ should create_file('apt-preferences').with({
+ :ensure => 'present',
+ :path => '/etc/apt/preferences',
+ :owner => 'root',
+ :group => 'root',
+ :mode => '0644',
+ :content => /Explanation/,
+ })
+ else
+ should create_file('apt-preferences').with({
+ :ensure => 'present',
+ :path => '/etc/apt/preferences',
+ :owner => 'root',
+ :group => 'root',
+ :mode => '0644',
+ :content => nil,
+ })
+ end
+ }
+
+ it {
+ if param_hash[:purge_preferences_d]
+ should create_file("preferences.d").with({
+ 'path' => "/etc/apt/preferences.d",
+ 'ensure' => "directory",
+ 'owner' => "root",
+ 'group' => "root",
+ 'purge' => true,
+ 'recurse' => true,
+ })
+ else
+ should create_file("preferences.d").with({
+ 'path' => "/etc/apt/preferences.d",
+ 'ensure' => "directory",
+ 'owner' => "root",
+ 'group' => "root",
+ 'purge' => false,
+ 'recurse' => false,
+ })
+ end
+ }
it {
should contain_exec("apt_update").with({
require 'spec_helper'
describe 'apt::debian::testing', :type => :class do
+ let(:facts) { { :lsbdistid => 'Debian' } }
it {
should contain_apt__source("debian_testing").with({
"location" => "http://debian.mirror.iweb.ca/debian/",
require 'spec_helper'
describe 'apt::debian::unstable', :type => :class do
+ let(:facts) { { :lsbdistid => 'Debian' } }
it {
should contain_apt__source("debian_unstable").with({
"location" => "http://debian.mirror.iweb.ca/debian/",
require 'spec_helper'
describe 'apt::params', :type => :class do
+ let(:facts) { { :lsbdistid => 'Debian' } }
let (:title) { 'my_package' }
it { should contain_apt__params }
require 'spec_helper'
describe 'apt::release', :type => :class do
+ let(:facts) { { :lsbdistid => 'Debian' } }
let (:title) { 'my_package' }
let :param_set do
describe 'apt::unattended_upgrades', :type => :class do
let(:file_unattended) { '/etc/apt/apt.conf.d/50unattended-upgrades' }
let(:file_periodic) { '/etc/apt/apt.conf.d/10periodic' }
+ let(:facts) { { :lsbdistid => 'Debian' } }
it { should contain_package("unattended-upgrades") }
require 'spec_helper'
describe 'apt::builddep', :type => :define do
+ let(:facts) { { :lsbdistid => 'Debian' } }
let(:title) { 'my_package' }
describe "should require apt-get update" do
require 'spec_helper'
describe 'apt::conf', :type => :define do
+ let(:facts) { { :lsbdistid => 'Debian' } }
let :title do
'norecommends'
end
require 'spec_helper'
describe 'apt::force', :type => :define do
+ let(:facts) { { :lsbdistid => 'Debian' } }
let :pre_condition do
'include apt::params'
end
require 'spec_helper'
describe 'apt::key', :type => :define do
+ let(:facts) { { :lsbdistid => 'Debian' } }
let :title do
'8347A27F'
end
require 'spec_helper'
describe 'apt::pin', :type => :define do
+ let(:facts) { { :lsbdistid => 'Debian' } }
let(:title) { 'my_pin' }
let :default_params do
}
end
- [
+ [
{ :params => {},
:content => "# my_pin\nExplanation: : my_pin\nPackage: *\nPin: release a=my_pin\nPin-Priority: 0\n"
},
{
:params => {
- :packages => 'apache',
+ :packages => 'apache',
:priority => '1'
},
:content => "# my_pin\nExplanation: : my_pin\nPackage: apache\nPin: release a=my_pin\nPin-Priority: 1\n"
},
{
:params => {
- :order => 50,
- :packages => 'apache',
+ :order => 50,
+ :packages => 'apache',
:priority => '1'
},
:content => "# my_pin\nExplanation: : my_pin\nPackage: apache\nPin: release a=my_pin\nPin-Priority: 1\n"
:priority => '1',
:origin => 'ftp.de.debian.org'
},
- :content => "# my_pin\nExplanation: : my_pin\nPackage: *\nPin: origin \"ftp.de.debian.org\"\nPin-Priority: 1\n"
+ :content => "# my_pin\nExplanation: : my_pin\nPackage: *\nPin: origin ftp.de.debian.org\nPin-Priority: 1\n"
},
{
:params => {
require 'spec_helper'
describe 'apt::ppa', :type => :define do
- [ { :lsbdistrelease => '11.04',
+ [
+ {
+ :lsbdistrelease => '11.04',
:lsbdistcodename => 'natty',
:operatingsystem => 'Ubuntu',
- :package => 'python-software-properties'},
- { :lsbdistrelease => '12.10',
+ :lsbdistid => 'Ubuntu',
+ :package => 'python-software-properties'
+ },
+ {
+ :lsbdistrelease => '12.10',
:lsbdistcodename => 'quantal',
:operatingsystem => 'Ubuntu',
- :package => 'software-properties-common'},
+ :lsbdistid => 'Ubuntu',
+ :package => 'software-properties-common'
+ },
].each do |platform|
context "on #{platform[:lsbdistcodename]}" do
let :facts do
{
- :lsbdistrelease => platform[:lsbdistrelease],
+ :lsbdistrelease => platform[:lsbdistrelease],
:lsbdistcodename => platform[:lsbdistcodename],
:operatingsystem => platform[:operatingsystem],
+ :lsbdistid => platform[:lsbdistid],
}
end
let :release do
end
let :facts do
{:lsbdistcodename => '#{platform[:lsbdistcodename]}',
- :operatingsystem => 'Ubuntu'}
+ :operatingsystem => 'Ubuntu',
+ :lsbdistid => 'Ubuntu'}
end
let(:title) { "ppa" }
let(:release) { "#{platform[:lsbdistcodename]}" }
require 'spec_helper'
describe 'apt::source', :type => :define do
+ let(:facts) { { :lsbdistid => 'Debian' } }
let :title do
'my_source'
end
end
let :facts do
- {:lsbdistcodename => 'karmic'}
+ {:lsbdistcodename => 'karmic', :lsbdistid => 'Ubuntu'}
end
let :params do
let(:default_params) { Hash.new }
let(:facts) { Hash.new }
it { expect { should raise_error(Puppet::Error) } }
- let(:facts) { { :lsbdistcodename => 'lucid' } }
+ let(:facts) { { :lsbdistcodename => 'lucid', :lsbdistid => 'Ubuntu' } }
it { should contain_apt__source(title) }
end
end
require 'beaker-rspec'
-hosts.each do |host|
- # Install Puppet
- install_package host, 'rubygems'
- on host, 'gem install puppet --no-ri --no-rdoc'
- on host, "mkdir -p #{host['distmoduledir']}"
+# Install Puppet
+unless ENV['RS_PROVISION'] == 'no'
+ hosts.each do |host|
+ if host.is_pe?
+ install_pe
+ else
+ install_puppet
+ on host, "mkdir -p #{host['distmoduledir']}"
+ end
+ end
end
+UNSUPPORTED_PLATFORMS = ['RedHat','Suse','windows','AIX','Solaris']
+
RSpec.configure do |c|
# Project root
proj_root = File.expand_path(File.join(File.dirname(__FILE__), '..'))
--- /dev/null
+require 'spec_helper'
+require 'puppet'
+
+describe Puppet::Type::type(:apt_key) do
+ context 'only namevar 32bit key id' do
+ let(:resource) { Puppet::Type.type(:apt_key).new(
+ :id => '4BD6EC30'
+ )}
+ it 'id is set' do
+ resource[:id].should eq '4BD6EC30'
+ end
+
+ it 'name is set to id' do
+ resource[:name].should eq '4BD6EC30'
+ end
+
+ it 'keyserver is default' do
+ resource[:server].should eq :'keyserver.ubuntu.com'
+ end
+
+ it 'source is not set' do
+ resource[:source].should eq nil
+ end
+
+ it 'content is not set' do
+ resource[:content].should eq nil
+ end
+ end
+
+ context 'with a lowercase 32bit key id' do
+ let(:resource) { Puppet::Type.type(:apt_key).new(
+ :id => '4bd6ec30'
+ )}
+ it 'id is set' do
+ resource[:id].should eq '4BD6EC30'
+ end
+ end
+
+ context 'with a 64bit key id' do
+ let(:resource) { Puppet::Type.type(:apt_key).new(
+ :id => 'FFFFFFFF4BD6EC30'
+ )}
+ it 'id is set' do
+ resource[:id].should eq '4BD6EC30'
+ end
+ end
+
+ context 'with a 0x formatted key id' do
+ let(:resource) { Puppet::Type.type(:apt_key).new(
+ :id => '0x4BD6EC30'
+ )}
+ it 'id is set' do
+ resource[:id].should eq '4BD6EC30'
+ end
+ end
+
+ context 'with a 0x formatted lowercase key id' do
+ let(:resource) { Puppet::Type.type(:apt_key).new(
+ :id => '0x4bd6ec30'
+ )}
+ it 'id is set' do
+ resource[:id].should eq '4BD6EC30'
+ end
+ end
+
+ context 'with a 0x formatted 64bit key id' do
+ let(:resource) { Puppet::Type.type(:apt_key).new(
+ :id => '0xFFFFFFFF4BD6EC30'
+ )}
+ it 'id is set' do
+ resource[:id].should eq '4BD6EC30'
+ end
+ end
+
+ context 'with source' do
+ let(:resource) { Puppet::Type.type(:apt_key).new(
+ :id => '4BD6EC30',
+ :source => 'http://apt.puppetlabs.com/pubkey.gpg'
+ )}
+
+ it 'source is set to the URL' do
+ resource[:source].should eq 'http://apt.puppetlabs.com/pubkey.gpg'
+ end
+ end
+
+ context 'with content' do
+ let(:resource) { Puppet::Type.type(:apt_key).new(
+ :id => '4BD6EC30',
+ :content => 'http://apt.puppetlabs.com/pubkey.gpg'
+ )}
+
+ it 'content is set to the string' do
+ resource[:content].should eq 'http://apt.puppetlabs.com/pubkey.gpg'
+ end
+ end
+
+ context 'with keyserver' do
+ let(:resource) { Puppet::Type.type(:apt_key).new(
+ :id => '4BD6EC30',
+ :server => 'http://keyring.debian.org'
+ )}
+
+ it 'keyserver is set to Debian' do
+ resource[:server].should eq 'http://keyring.debian.org'
+ end
+ end
+
+ context 'validation' do
+ it 'raises an error if content and source are set' do
+ expect { Puppet::Type.type(:apt_key).new(
+ :id => '4BD6EC30',
+ :source => 'http://apt.puppetlabs.com/pubkey.gpg',
+ :content => 'Completely invalid as a GPG key'
+ )}.to raise_error(/content and source are mutually exclusive/)
+ end
+
+ it 'raises an error if a weird length key is used' do
+ expect { Puppet::Type.type(:apt_key).new(
+ :id => 'F4BD6EC30',
+ :source => 'http://apt.puppetlabs.com/pubkey.gpg',
+ :content => 'Completely invalid as a GPG key'
+ )}.to raise_error(/Valid values match/)
+ end
+
+ it 'raises an error when an invalid URI scheme is used in source' do
+ expect { Puppet::Type.type(:apt_key).new(
+ :id => '4BD6EC30',
+ :source => 'hkp://pgp.mit.edu'
+ )}.to raise_error(/Valid values match/)
+ end
+
+ it 'allows the http URI scheme in source' do
+ expect { Puppet::Type.type(:apt_key).new(
+ :id => '4BD6EC30',
+ :source => 'http://pgp.mit.edu'
+ )}.to_not raise_error
+ end
+
+ it 'allows the https URI scheme in source' do
+ expect { Puppet::Type.type(:apt_key).new(
+ :id => '4BD6EC30',
+ :source => 'https://pgp.mit.edu'
+ )}.to_not raise_error
+ end
+
+ it 'allows the ftp URI scheme in source' do
+ expect { Puppet::Type.type(:apt_key).new(
+ :id => '4BD6EC30',
+ :source => 'ftp://pgp.mit.edu'
+ )}.to_not raise_error
+ end
+
+ it 'allows an absolute path in source' do
+ expect { Puppet::Type.type(:apt_key).new(
+ :id => '4BD6EC30',
+ :source => '/path/to/a/file'
+ )}.to_not raise_error
+ end
+ end
+end
elsif @version.length > 0
@pin = "version #{@version}"
elsif @origin.length > 0
- @pin = "origin \"#{@origin}\""
+ @pin = "origin #{@origin}"
end
-%>
# <%= @name %>