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 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388
|
require 'spec_helper'
require 'shared_behaviours/all_parsedfile_providers'
# TODO: We've recently dropped running specs on Solaris because it was poor ROI.
# This file has a ton of tiptoeing around Solaris that we should ultimately
# remove, but I don't want to do so just yet, in case we get pushback to
# restore Solaris spec tests.
describe Puppet::Type.type(:mount).provider(:parsed), unless: Puppet.features.microsoft_windows? do
before :each do
Facter.clear
end
let :vfstab_sample do
"/dev/dsk/c0d0s0 /dev/rdsk/c0d0s0 \t\t / \t ufs 1 no\t-"
end
let :fstab_sample do
"/dev/vg00/lv01\t/spare \t \t ext3 defaults\t1 2"
end
# LAK:FIXME I can't mock Facter because this test happens at parse-time.
it 'defaults to /etc/vfstab on Solaris' do
if Facter.value(:osfamily) != 'Solaris'
skip('This test only works on Solaris')
else
expect(described_class.default_target).to eq('/etc/vfstab')
end
end
it 'defaults to /etc/filesystems on AIX' do
pending 'This test only works on AIX' unless Facter.value(:osfamily) == 'AIX'
expect(described_class.default_target).to eq('/etc/filesystems')
end
it 'defaults to /etc/fstab on anything else' do
if Facter.value(:osfamily) == 'Solaris'
skip('This test only does not work on Solaris')
else
expect(described_class.default_target).to eq('/etc/fstab')
end
end
describe 'when parsing a line' do
it 'does not crash on incomplete lines in fstab' do
parse = described_class.parse <<-FSTAB
/dev/incomplete
/dev/device name
FSTAB
expect { described_class.to_line(parse[0]) }.not_to raise_error
end
# it_should_behave_like "all parsedfile providers",
# provider_class, my_fixtures('*.fstab')
describe 'on Solaris', if: Facter.value(:osfamily) == 'Solaris' do
it 'extracts device from the first field' do
expect(described_class.parse_line(vfstab_sample)[:device]).to eq('/dev/dsk/c0d0s0')
end
it 'extracts blockdevice from second field' do
expect(described_class.parse_line(vfstab_sample)[:blockdevice]).to eq('/dev/rdsk/c0d0s0')
end
it 'extracts name from third field' do
expect(described_class.parse_line(vfstab_sample)[:name]).to eq('/')
end
it 'extracts fstype from fourth field' do
expect(described_class.parse_line(vfstab_sample)[:fstype]).to eq('ufs')
end
it 'extracts pass from fifth field' do
expect(described_class.parse_line(vfstab_sample)[:pass]).to eq('1')
end
it 'extracts atboot from sixth field' do
expect(described_class.parse_line(vfstab_sample)[:atboot]).to eq('no')
end
it 'extracts options from seventh field' do
expect(described_class.parse_line(vfstab_sample)[:options]).to eq('-')
end
end
describe 'on other platforms than Solaris', if: Facter.value(:osfamily) != 'Solaris' do
it 'extracts device from the first field' do
expect(described_class.parse_line(fstab_sample)[:device]).to eq('/dev/vg00/lv01')
end
it 'extracts name from second field' do
expect(described_class.parse_line(fstab_sample)[:name]).to eq('/spare')
end
it 'extracts fstype from third field' do
expect(described_class.parse_line(fstab_sample)[:fstype]).to eq('ext3')
end
it 'extracts options from fourth field' do
expect(described_class.parse_line(fstab_sample)[:options]).to eq('defaults')
end
it 'extracts dump from fifth field' do
expect(described_class.parse_line(fstab_sample)[:dump]).to eq('1')
end
it 'extracts options from sixth field' do
expect(described_class.parse_line(fstab_sample)[:pass]).to eq('2')
end
end
end
describe 'mountinstances' do
it 'gets name from mountoutput found on Solaris' do
Facter.stubs(:value).with(:osfamily).returns 'Solaris'
described_class.stubs(:mountcmd).returns(File.read(my_fixture('solaris.mount')))
mounts = described_class.mountinstances
expect(mounts.size).to eq(6)
expect(mounts[0]).to eq(name: '/', mounted: :yes)
expect(mounts[1]).to eq(name: '/proc', mounted: :yes)
expect(mounts[2]).to eq(name: '/etc/mnttab', mounted: :yes)
expect(mounts[3]).to eq(name: '/tmp', mounted: :yes)
expect(mounts[4]).to eq(name: '/export/home', mounted: :yes)
expect(mounts[5]).to eq(name: '/ghost', mounted: :yes)
end
it 'gets name from mountoutput found on HP-UX' do
Facter.stubs(:value).with(:osfamily).returns 'HP-UX'
described_class.stubs(:mountcmd).returns(File.read(my_fixture('hpux.mount')))
mounts = described_class.mountinstances
expect(mounts.size).to eq(17)
expect(mounts[0]).to eq(name: '/', mounted: :yes)
expect(mounts[1]).to eq(name: '/devices', mounted: :yes)
expect(mounts[2]).to eq(name: '/dev', mounted: :yes)
expect(mounts[3]).to eq(name: '/system/contract', mounted: :yes)
expect(mounts[4]).to eq(name: '/proc', mounted: :yes)
expect(mounts[5]).to eq(name: '/etc/mnttab', mounted: :yes)
expect(mounts[6]).to eq(name: '/etc/svc/volatile', mounted: :yes)
expect(mounts[7]).to eq(name: '/system/object', mounted: :yes)
expect(mounts[8]).to eq(name: '/etc/dfs/sharetab', mounted: :yes)
expect(mounts[9]).to eq(name: '/lib/libc.so.1', mounted: :yes)
expect(mounts[10]).to eq(name: '/dev/fd', mounted: :yes)
expect(mounts[11]).to eq(name: '/tmp', mounted: :yes)
expect(mounts[12]).to eq(name: '/var/run', mounted: :yes)
expect(mounts[13]).to eq(name: '/export', mounted: :yes)
expect(mounts[14]).to eq(name: '/export/home', mounted: :yes)
expect(mounts[15]).to eq(name: '/rpool', mounted: :yes)
expect(mounts[16]).to eq(name: '/ghost', mounted: :yes)
end
it 'gets name from mountoutput found on Darwin' do
Facter.stubs(:value).with(:osfamily).returns 'Darwin'
described_class.stubs(:mountcmd).returns(File.read(my_fixture('darwin.mount')))
mounts = described_class.mountinstances
expect(mounts.size).to eq(6)
expect(mounts[0]).to eq(name: '/', mounted: :yes)
expect(mounts[1]).to eq(name: '/dev', mounted: :yes)
expect(mounts[2]).to eq(name: '/net', mounted: :yes)
expect(mounts[3]).to eq(name: '/home', mounted: :yes)
expect(mounts[4]).to eq(name: '/usr', mounted: :yes)
expect(mounts[5]).to eq(name: '/ghost', mounted: :yes)
end
it 'gets name from mountoutput found on Linux' do
Facter.stubs(:value).with(:osfamily).returns 'Gentoo'
described_class.stubs(:mountcmd).returns(File.read(my_fixture('linux.mount')))
mounts = described_class.mountinstances
expect(mounts[0]).to eq(name: '/', mounted: :yes)
expect(mounts[1]).to eq(name: '/lib64/rc/init.d', mounted: :yes)
expect(mounts[2]).to eq(name: '/sys', mounted: :yes)
expect(mounts[3]).to eq(name: '/usr/portage', mounted: :yes)
expect(mounts[4]).to eq(name: '/ghost', mounted: :yes)
expect(mounts[5]).to eq(name: '/run', mounted: :yes)
expect(mounts[6]).to eq(name: '/white space', mounted: :yes)
end
it 'gets name from mountoutput found on AIX' do
Facter.stubs(:value).with(:osfamily).returns 'AIX'
described_class.stubs(:mountcmd).returns(File.read(my_fixture('aix.mount')))
mounts = described_class.mountinstances
expect(mounts[0]).to eq(name: '/', mounted: :yes)
expect(mounts[1]).to eq(name: '/usr', mounted: :yes)
expect(mounts[2]).to eq(name: '/var', mounted: :yes)
expect(mounts[3]).to eq(name: '/tmp', mounted: :yes)
expect(mounts[4]).to eq(name: '/home', mounted: :yes)
expect(mounts[5]).to eq(name: '/admin', mounted: :yes)
expect(mounts[6]).to eq(name: '/proc', mounted: :yes)
expect(mounts[7]).to eq(name: '/opt', mounted: :yes)
expect(mounts[8]).to eq(name: '/srv/aix', mounted: :yes)
end
it 'raises an error if a line is not understandable' do
described_class.stubs(:mountcmd).returns('bazinga!')
expect { described_class.mountinstances }.to raise_error Puppet::Error, 'Could not understand line bazinga! from mount output'
end
end
it "supports AIX's paragraph based /etc/filesystems" do
pending 'This test only works on AIX' unless Facter.value(:osfamily) == 'AIX'
Facter.stubs(:value).with(:osfamily).returns 'AIX'
described_class.stubs(:default_target).returns my_fixture('aix.filesystems')
described_class.stubs(:mountcmd).returns File.read(my_fixture('aix.mount'))
instances = described_class.instances
expect(instances[0].name).to eq('/')
expect(instances[0].device).to eq('/dev/hd4')
expect(instances[0].fstype).to eq('jfs2')
expect(instances[0].options).to eq('check=false,free=true,log=NULL,mount=automatic,quota=no,type=bootfs,vol=root')
expect(instances[11].name).to eq('/srv/aix')
expect(instances[11].device).to eq('mynode')
expect(instances[11].fstype).to eq('nfs')
expect(instances[11].options).to eq('vers=2,account=false,log=NULL,mount=true')
end
my_fixtures('*.fstab').each do |fstab|
platform = File.basename(fstab, '.fstab')
describe "when calling instances on #{platform}" do
let(:instances) do
described_class.instances.map { |prov| { name: prov.get(:name), ensure: prov.get(:ensure) } }
end
before :each do
Facter.stubs(:value).with(:osfamily).returns platform
if Facter[:osfamily] == 'Solaris'
platform == 'solaris' ||
skip("We need to stub the operatingsystem fact at load time, but can't")
else
platform != 'solaris' ||
skip("We need to stub the operatingsystem fact at load time, but can't")
end
# Stub the mount output to our fixture.
begin
mount = my_fixture(platform + '.mount')
described_class.stubs(:mountcmd).returns File.read(mount)
rescue
skip "is #{platform}.mount missing at this point?"
end
# Note: we have to stub default_target before creating resources
# because it is used by Puppet::Type::Mount.new to populate the
# :target property.
described_class.stubs(:default_target).returns fstab
end
# Following mountpoint are present in all fstabs/mountoutputs
describe 'on other platforms than Solaris', if: Facter.value(:osfamily) != 'Solaris' do
it 'includes unmounted resources' do
expect(instances).to include(name: '/', ensure: :mounted)
end
it 'includes mounted resources' do
expect(instances).to include(name: '/boot', ensure: :unmounted)
end
it 'includes ghost resources' do
expect(instances).to include(name: '/ghost', ensure: :ghost)
end
end
end
describe 'when prefetching on Linux' do
let(:res_ghost_whitespace) { Puppet::Type::Mount.new(name: '/ghost white space') } # in no fake fstab
let(:res_trailing_whitespace) { Puppet::Type::Mount.new(name: '/trailing white space/') } # in Linux fake fstab
let(:res_mounted_whitespace) { Puppet::Type::Mount.new(name: '/white space') } # in Linux fake fstab
let(:res_unmounted_whitespace) { Puppet::Type::Mount.new(name: '/unmounted white space') } # in Linux fake fstab
let(:res_absent_whitespace) { Puppet::Type::Mount.new(name: '/absent white space') } # in no fake fstab
let(:resource_hash) do
hash = {}
[res_ghost_whitespace, res_trailing_whitespace, res_mounted_whitespace, res_unmounted_whitespace, res_absent_whitespace].each do |resource|
hash[resource.name] = resource
end
hash
end
before :each do
Facter.stubs(:value).with(:kernel).returns 'Linux'
Facter.stubs(:value).with(:operatingsystem).returns 'RedHat'
Facter.stubs(:value).with(:osfamily).returns 'RedHat'
begin
mount = my_fixture('linux.mount')
described_class.stubs(:mountcmd).returns File.read(mount)
rescue
skip 'is linux.mount missing at this point?'
end
described_class.stubs(:default_target).returns my_fixture('linux.fstab')
end
describe 'when handling whitespaces in mountpoints' do
it 'sets :ensure to :mounted if found in fstab and mounted' do
described_class.prefetch(resource_hash)
expect(res_mounted_whitespace.provider.get(:ensure)).to eq(:mounted)
end
it 'sets :ensure to :unmounted if found in fstab but not mounted' do
described_class.prefetch(resource_hash)
expect(res_unmounted_whitespace.provider.get(:ensure)).to eq(:unmounted)
end
it 'sets :ensure to :ghost if not found in fstab but mounted' do
described_class.prefetch(resource_hash)
expect(res_ghost_whitespace.provider.get(:ensure)).to eq(:ghost)
end
it 'strips trailing slashes from resource titles' do
described_class.prefetch(resource_hash)
expect(res_trailing_whitespace.provider.get(:ensure)).to eq(:mounted)
end
it 'sets :ensure to :absent if not found in fstab and not mounted' do
described_class.prefetch(resource_hash)
expect(res_absent_whitespace.provider.get(:ensure)).to eq(:absent)
end
end
end
describe "when prefetching on #{platform}" do
let(:res_ghost) { Puppet::Type::Mount.new(name: '/ghost') } # in no fake fstab
let(:res_mounted) { Puppet::Type::Mount.new(name: '/') } # in every fake fstab
let(:res_unmounted) { Puppet::Type::Mount.new(name: '/boot') } # in every fake fstab
let(:res_absent) { Puppet::Type::Mount.new(name: '/absent') } # in no fake fstab
let(:res_trailing_slash) { Puppet::Type::Mount.new(name: '/run/') } # in Linux fake fstab
let(:resource_hash) do
# Simulate transaction.rb:prefetch
hash = {}
[res_ghost, res_mounted, res_unmounted, res_absent, res_trailing_slash].each do |resource|
hash[resource.name] = resource
end
hash
end
before :each do
[:osfamily, :operatingsystem, :kernel].each do |fact|
Facter.stubs(:value).with(fact).returns platform
end
if Facter[:osfamily] == 'Solaris'
platform == 'solaris' ||
skip("We need to stub the operatingsystem fact at load time, but can't")
else
platform != 'solaris' ||
skip("We need to stub the operatingsystem fact at load time, but can't")
end
# Stub the mount output to our fixture.
begin
mount = my_fixture(platform + '.mount')
described_class.stubs(:mountcmd).returns File.read(mount)
rescue
skip "is #{platform}.mount missing at this point?"
end
# Note: we have to stub default_target before creating resources
# because it is used by Puppet::Type::Mount.new to populate the
# :target property.
described_class.stubs(:default_target).returns fstab
end
describe 'on other platforms than Solaris', if: Facter.value(:osfamily) != 'Solaris' do
it 'sets :ensure to :unmounted if found in fstab but not mounted' do
described_class.prefetch(resource_hash)
expect(res_unmounted.provider.get(:ensure)).to eq(:unmounted)
end
it 'sets :ensure to :ghost if not found in fstab but mounted' do
described_class.prefetch(resource_hash)
expect(res_ghost.provider.get(:ensure)).to eq(:ghost)
end
it 'sets :ensure to :mounted if found in fstab and mounted' do
described_class.prefetch(resource_hash)
expect(res_mounted.provider.get(:ensure)).to eq(:mounted)
end
it 'strips trailing slashes from resource titles' do
described_class.prefetch(resource_hash)
expect(res_trailing_slash.provider.get(:ensure)).to eq(:mounted)
end
end
it 'sets :ensure to :absent if not found in fstab and not mounted' do
described_class.prefetch(resource_hash)
expect(res_absent.provider.get(:ensure)).to eq(:absent)
end
end
end
end
|