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
|
require 'spec_helper'
require 'puppet/face'
describe Puppet::Face[:help, '0.0.1'] do
it 'has a help action' do
expect(subject).to be_action :help
end
it 'has a default action of help' do
expect(subject.get_action('help')).to be_default
end
it 'accepts a call with no arguments' do
expect {
subject.help()
}.to_not raise_error
end
it 'accepts a face name' do
expect { subject.help(:help) }.to_not raise_error
end
it 'accepts a face and action name' do
expect { subject.help(:help, :help) }.to_not raise_error
end
it 'fails if more than a face and action are given' do
expect { subject.help(:help, :help, :for_the_love_of_god) }.to raise_error ArgumentError
end
it "treats :current and 'current' identically" do
expect(subject.help(:help, :version => :current)).to eq(
subject.help(:help, :version => 'current')
)
end
it 'raises an error when the face is unavailable' do
expect {
subject.help(:huzzah, :bar, :version => '17.0.0')
}.to raise_error(ArgumentError, /Could not find version 17\.0\.0/)
end
it 'finds a face by version' do
face = Puppet::Face[:huzzah, :current]
expect(subject.help(:huzzah, :version => face.version)).
to eq(subject.help(:huzzah, :version => :current))
end
context 'rendering has an error' do
it 'raises an ArgumentError if the face raises a StandardError' do
face = Puppet::Face[:module, :current]
allow(face).to receive(:short_description).and_raise(StandardError, 'whoops')
expect {
subject.help(:module)
}.to raise_error(ArgumentError, /Detail: "whoops"/)
end
it 'raises an ArgumentError if the face raises a LoadError' do
face = Puppet::Face[:module, :current]
allow(face).to receive(:short_description).and_raise(LoadError, 'cannot load such file -- yard')
expect {
subject.help(:module)
}.to raise_error(ArgumentError, /Detail: "cannot load such file -- yard"/)
end
context 'with face actions' do
it 'returns an error if we can not get an action for the module' do
face = Puppet::Face[:module, :current]
allow(face).to receive(:get_action).and_return(nil)
expect {subject.help('module', 'list')}.to raise_error(ArgumentError, /Unable to load action list from Puppet::Face/)
end
end
end
context 'when listing subcommands' do
subject { Puppet::Face[:help, :current].help }
RSpec::Matchers.define :have_a_summary do
match do |instance|
instance.summary.is_a?(String)
end
end
# Check a precondition for the next block; if this fails you have
# something odd in your set of face, and we skip testing things that
# matter. --daniel 2011-04-10
it 'has at least one face with a summary' do
expect(Puppet::Face.faces).to be_any do |name|
Puppet::Face[name, :current].summary
end
end
it 'lists all faces which are runnable from the command line' do
help_face = Puppet::Face[:help, :current]
# The main purpose of the help face is to provide documentation for
# command line users. It shouldn't show documentation for faces
# that can't be run from the command line, so, rather than iterating
# over all available faces, we need to iterate over the subcommands
# that are available from the command line.
Puppet::Application.available_application_names.each do |name|
next unless help_face.is_face_app?(name)
next if help_face.exclude_from_docs?(name)
face = Puppet::Face[name, :current]
summary = face.summary
expect(subject).to match(%r{ #{name} })
summary and expect(subject).to match(%r{ #{name} +#{summary}})
end
end
context 'face summaries' do
it 'can generate face summaries' do
faces = Puppet::Face.faces
expect(faces.length).to be > 0
faces.each do |name|
expect(Puppet::Face[name, :current]).to have_a_summary
end
end
end
it 'lists all legacy applications' do
Puppet::Face[:help, :current].legacy_applications.each do |appname|
expect(subject).to match(%r{ #{appname} })
summary = Puppet::Face[:help, :current].horribly_extract_summary_from(appname)
summary_regex = Regexp.escape(summary)
summary and expect(subject).to match(%r{ #{summary_regex}$})
end
end
end
context 'deprecated faces' do
it 'prints a deprecation warning for deprecated faces' do
allow(Puppet::Face[:module, :current]).to receive(:deprecated?).and_return(true)
expect(Puppet::Face[:help, :current].help(:module)).to match(/Warning: 'puppet module' is deprecated/)
end
end
context '#all_application_summaries' do
it 'appends a deprecation warning for deprecated faces' do
# Stub the module face as deprecated
expect(Puppet::Face[:module, :current]).to receive(:deprecated?).and_return(true)
Puppet::Face[:help, :current].all_application_summaries.each do |appname,summary|
expect(summary).to match(/Deprecated/) if appname == 'module'
end
end
end
context '#legacy_applications' do
subject { Puppet::Face[:help, :current].legacy_applications }
# If we don't, these tests are ... less than useful, because they assume
# it. When this breaks you should consider ditching the entire feature
# and tests, but if not work out how to fake one. --daniel 2011-04-11
it { expect(subject.count).to be > 1 }
# Meh. This is nasty, but we can't control the other list; the specific
# bug that caused these to be listed is annoyingly subtle and has a nasty
# fix, so better to have a "fail if you do something daft" trigger in
# place here, I think. --daniel 2011-04-11
%w{face_base indirection_base}.each do |name|
it { is_expected.not_to include name }
end
end
context 'help for legacy applications' do
subject { Puppet::Face[:help, :current] }
let :appname do subject.legacy_applications.first end
# This test is purposely generic, so that as we eliminate legacy commands
# we don't get into a loop where we either test a face-based replacement
# and fail to notice breakage, or where we have to constantly rewrite this
# test and all. --daniel 2011-04-11
it 'returns the legacy help when given the subcommand' do
help = subject.help(appname)
expect(help).to match(/puppet-#{appname}/)
%w{SYNOPSIS USAGE DESCRIPTION OPTIONS COPYRIGHT}.each do |heading|
expect(help).to match(/^#{heading}$/)
end
end
it 'fails when asked for an action on a legacy command' do
expect { subject.help(appname, :whatever) }.
to raise_error(ArgumentError, /The legacy subcommand '#{appname}' does not support supplying an action/)
end
context 'rendering has an error' do
it 'raises an ArgumentError if a legacy application raises a StandardError' do
allow_any_instance_of(Puppet::Application[appname].class).to receive(:help).and_raise(StandardError, 'whoops')
expect {
subject.help(appname)
}.to raise_error(ArgumentError, /Detail: "whoops"/)
end
it 'raises an ArgumentError if a legacy application raises a LoadError' do
allow_any_instance_of(Puppet::Application[appname].class).to receive(:help).and_raise(LoadError, 'cannot load such file -- yard')
expect {
subject.help(appname)
}.to raise_error(ArgumentError, /Detail: "cannot load such file -- yard"/)
end
end
end
end
|