puppet 6.11.1-x64-mingw32 → 6.16.0-x64-mingw32
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of puppet might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/CODEOWNERS +3 -8
- data/CONTRIBUTING.md +7 -13
- data/Gemfile +1 -0
- data/Gemfile.lock +39 -36
- data/README.md +17 -24
- data/ext/build_defaults.yaml +1 -0
- data/ext/project_data.yaml +1 -1
- data/ext/windows/service/daemon.rb +25 -20
- data/lib/puppet.rb +52 -13
- data/lib/puppet/agent.rb +20 -14
- data/lib/puppet/application/agent.rb +12 -14
- data/lib/puppet/application/describe.rb +7 -5
- data/lib/puppet/application/device.rb +2 -2
- data/lib/puppet/application/filebucket.rb +19 -15
- data/lib/puppet/application/plugin.rb +1 -0
- data/lib/puppet/application/resource.rb +1 -1
- data/lib/puppet/application/ssl.rb +4 -4
- data/lib/puppet/concurrent.rb +2 -0
- data/lib/puppet/concurrent/lock.rb +16 -0
- data/lib/puppet/concurrent/synchronized.rb +15 -0
- data/lib/puppet/concurrent/thread_local_singleton.rb +14 -0
- data/lib/puppet/configurer.rb +85 -83
- data/lib/puppet/configurer/plugin_handler.rb +10 -1
- data/lib/puppet/context/trusted_information.rb +14 -8
- data/lib/puppet/daemon.rb +13 -27
- data/lib/puppet/defaults.rb +158 -40
- data/lib/puppet/environments.rb +30 -20
- data/lib/puppet/error.rb +9 -1
- data/lib/puppet/face/facts.rb +8 -5
- data/lib/puppet/face/help.rb +29 -3
- data/lib/puppet/face/module/search.rb +5 -0
- data/lib/puppet/face/plugin.rb +2 -2
- data/lib/puppet/file_serving/http_metadata.rb +1 -1
- data/lib/puppet/file_system/file_impl.rb +13 -9
- data/lib/puppet/file_system/memory_file.rb +6 -0
- data/lib/puppet/file_system/memory_impl.rb +13 -0
- data/lib/puppet/file_system/uniquefile.rb +4 -0
- data/lib/puppet/file_system/windows.rb +7 -10
- data/lib/puppet/forge.rb +3 -3
- data/lib/puppet/forge/errors.rb +2 -2
- data/lib/puppet/forge/repository.rb +31 -86
- data/lib/puppet/functions/call.rb +1 -1
- data/lib/puppet/functions/camelcase.rb +2 -2
- data/lib/puppet/functions/epp.rb +4 -4
- data/lib/puppet/functions/eyaml_lookup_key.rb +13 -8
- data/lib/puppet/functions/filter.rb +1 -0
- data/lib/puppet/functions/find_file.rb +9 -9
- data/lib/puppet/functions/find_template.rb +63 -0
- data/lib/puppet/functions/inline_epp.rb +5 -5
- data/lib/puppet/functions/reduce.rb +2 -4
- data/lib/puppet/http.rb +7 -0
- data/lib/puppet/http/client.rb +341 -54
- data/lib/puppet/http/errors.rb +2 -0
- data/lib/puppet/http/external_client.rb +90 -0
- data/lib/puppet/http/redirector.rb +34 -0
- data/lib/puppet/http/resolver.rb +57 -1
- data/lib/puppet/http/resolver/server_list.rb +98 -0
- data/lib/puppet/http/resolver/settings.rb +23 -2
- data/lib/puppet/http/resolver/srv.rb +36 -4
- data/lib/puppet/http/response.rb +68 -1
- data/lib/puppet/http/retry_after_handler.rb +39 -0
- data/lib/puppet/http/service.rb +179 -3
- data/lib/puppet/http/service/ca.rb +84 -21
- data/lib/puppet/http/service/compiler.rb +319 -0
- data/lib/puppet/http/service/file_server.rb +206 -0
- data/lib/puppet/http/service/report.rb +66 -0
- data/lib/puppet/http/session.rb +106 -31
- data/lib/puppet/indirector/catalog/compiler.rb +10 -0
- data/lib/puppet/indirector/catalog/rest.rb +34 -0
- data/lib/puppet/indirector/facts/rest.rb +42 -0
- data/lib/puppet/indirector/file_bucket_file/file.rb +1 -1
- data/lib/puppet/indirector/file_bucket_file/rest.rb +48 -0
- data/lib/puppet/indirector/file_content/http.rb +5 -0
- data/lib/puppet/indirector/file_content/rest.rb +30 -0
- data/lib/puppet/indirector/file_metadata/http.rb +4 -4
- data/lib/puppet/indirector/file_metadata/rest.rb +52 -0
- data/lib/puppet/indirector/json.rb +1 -1
- data/lib/puppet/indirector/msgpack.rb +1 -1
- data/lib/puppet/indirector/node/rest.rb +24 -0
- data/lib/puppet/indirector/report/rest.rb +19 -0
- data/lib/puppet/indirector/report/yaml.rb +23 -0
- data/lib/puppet/indirector/rest.rb +12 -0
- data/lib/puppet/indirector/status/rest.rb +18 -0
- data/lib/puppet/loaders.rb +6 -0
- data/lib/puppet/metatype/manager.rb +80 -80
- data/lib/puppet/network/http/base_pool.rb +19 -1
- data/lib/puppet/network/http/compression.rb +7 -0
- data/lib/puppet/network/http/connection.rb +6 -0
- data/lib/puppet/network/http/connection_adapter.rb +182 -0
- data/lib/puppet/network/http/nocache_pool.rb +2 -0
- data/lib/puppet/network/http/pool.rb +13 -6
- data/lib/puppet/network/http_pool.rb +2 -1
- data/lib/puppet/node/environment.rb +24 -8
- data/lib/puppet/pal/catalog_compiler.rb +5 -0
- data/lib/puppet/pal/pal_impl.rb +9 -29
- data/lib/puppet/parser/ast/pops_bridge.rb +6 -11
- data/lib/puppet/parser/compiler.rb +42 -32
- data/lib/puppet/parser/functions.rb +18 -13
- data/lib/puppet/parser/functions/epp.rb +3 -3
- data/lib/puppet/parser/functions/filter.rb +1 -0
- data/lib/puppet/parser/functions/inline_epp.rb +5 -5
- data/lib/puppet/pops/evaluator/access_operator.rb +2 -2
- data/lib/puppet/pops/evaluator/evaluator_impl.rb +1 -1
- data/lib/puppet/pops/evaluator/runtime3_support.rb +1 -1
- data/lib/puppet/pops/loader/puppet_plan_instantiator.rb +12 -3
- data/lib/puppet/pops/loaders.rb +7 -5
- data/lib/puppet/pops/lookup/invocation.rb +10 -3
- data/lib/puppet/pops/model/pn_transformer.rb +5 -9
- data/lib/puppet/pops/parser/evaluating_parser.rb +8 -11
- data/lib/puppet/pops/serialization/json_path.rb +3 -3
- data/lib/puppet/pops/time/timespan.rb +3 -5
- data/lib/puppet/pops/types/p_object_type_extension.rb +10 -0
- data/lib/puppet/pops/types/string_converter.rb +6 -9
- data/lib/puppet/pops/types/type_calculator.rb +30 -10
- data/lib/puppet/pops/types/type_formatter.rb +9 -11
- data/lib/puppet/pops/types/type_parser.rb +3 -3
- data/lib/puppet/pops/validation/checker4_0.rb +1 -1
- data/lib/puppet/pops/validation/tasks_checker.rb +5 -1
- data/lib/puppet/provider/aix_object.rb +4 -2
- data/lib/puppet/provider/group/aix.rb +1 -0
- data/lib/puppet/provider/group/groupadd.rb +57 -24
- data/lib/puppet/provider/group/windows_adsi.rb +3 -3
- data/lib/puppet/provider/package/aix.rb +17 -2
- data/lib/puppet/provider/package/apt.rb +78 -4
- data/lib/puppet/provider/package/dnfmodule.rb +69 -15
- data/lib/puppet/provider/package/dpkg.rb +14 -7
- data/lib/puppet/provider/package/fink.rb +20 -3
- data/lib/puppet/provider/package/gem.rb +41 -7
- data/lib/puppet/provider/package/openbsd.rb +13 -1
- data/lib/puppet/provider/package/pacman.rb +2 -5
- data/lib/puppet/provider/package/pip.rb +143 -48
- data/lib/puppet/provider/package/pip3.rb +0 -2
- data/lib/puppet/provider/package/pkg.rb +18 -5
- data/lib/puppet/provider/package/pkgdmg.rb +1 -1
- data/lib/puppet/provider/package/pkgng.rb +16 -4
- data/lib/puppet/provider/package/portage.rb +5 -5
- data/lib/puppet/provider/package/puppet_gem.rb +6 -2
- data/lib/puppet/provider/package/rpm.rb +6 -213
- data/lib/puppet/provider/package/yum.rb +108 -24
- data/lib/puppet/provider/package/zypper.rb +59 -1
- data/lib/puppet/provider/package_targetable.rb +5 -4
- data/lib/puppet/provider/service/systemd.rb +23 -5
- data/lib/puppet/provider/user/aix.rb +1 -0
- data/lib/puppet/provider/user/directoryservice.rb +30 -5
- data/lib/puppet/provider/user/hpux.rb +1 -1
- data/lib/puppet/provider/user/useradd.rb +11 -8
- data/lib/puppet/reports/http.rb +13 -9
- data/lib/puppet/reports/store.rb +1 -1
- data/lib/puppet/resource/type_collection.rb +20 -16
- data/lib/puppet/runtime.rb +32 -1
- data/lib/puppet/settings.rb +4 -0
- data/lib/puppet/settings/http_extra_headers_setting.rb +25 -0
- data/lib/puppet/ssl.rb +1 -0
- data/lib/puppet/ssl/certificate.rb +2 -1
- data/lib/puppet/ssl/host.rb +4 -4
- data/lib/puppet/ssl/oids.rb +1 -0
- data/lib/puppet/ssl/ssl_provider.rb +20 -0
- data/lib/puppet/ssl/state_machine.rb +81 -35
- data/lib/puppet/ssl/verifier_adapter.rb +9 -1
- data/lib/puppet/test/test_helper.rb +7 -1
- data/lib/puppet/transaction.rb +33 -11
- data/lib/puppet/transaction/report.rb +2 -2
- data/lib/puppet/transaction/resource_harness.rb +1 -1
- data/lib/puppet/type.rb +7 -2
- data/lib/puppet/type/file.rb +13 -0
- data/lib/puppet/type/file/data_sync.rb +5 -1
- data/lib/puppet/type/file/source.rb +49 -58
- data/lib/puppet/type/group.rb +5 -4
- data/lib/puppet/type/package.rb +102 -10
- data/lib/puppet/type/service.rb +6 -8
- data/lib/puppet/type/user.rb +6 -30
- data/lib/puppet/util.rb +34 -11
- data/lib/puppet/util/at_fork.rb +1 -1
- data/lib/puppet/util/autoload.rb +4 -18
- data/lib/puppet/util/instance_loader.rb +14 -10
- data/lib/puppet/util/log/destinations.rb +2 -11
- data/lib/puppet/util/logging.rb +30 -18
- data/lib/puppet/util/package/version/debian.rb +175 -0
- data/lib/puppet/util/package/version/gem.rb +15 -0
- data/lib/puppet/util/package/version/pip.rb +167 -0
- data/lib/puppet/util/package/version/range.rb +53 -0
- data/lib/puppet/util/package/version/range/eq.rb +14 -0
- data/lib/puppet/util/package/version/range/gt.rb +14 -0
- data/lib/puppet/util/package/version/range/gt_eq.rb +14 -0
- data/lib/puppet/util/package/version/range/lt.rb +14 -0
- data/lib/puppet/util/package/version/range/lt_eq.rb +14 -0
- data/lib/puppet/util/package/version/range/min_max.rb +21 -0
- data/lib/puppet/util/package/version/range/simple.rb +11 -0
- data/lib/puppet/util/package/version/rpm.rb +73 -0
- data/lib/puppet/util/pidlock.rb +36 -10
- data/lib/puppet/util/platform.rb +5 -0
- data/lib/puppet/util/plist.rb +6 -0
- data/lib/puppet/util/rpm_compare.rb +193 -0
- data/lib/puppet/util/storage.rb +0 -1
- data/lib/puppet/util/windows/adsi.rb +50 -20
- data/lib/puppet/util/windows/process.rb +15 -14
- data/lib/puppet/util/windows/security.rb +1 -0
- data/lib/puppet/util/windows/sid.rb +3 -3
- data/lib/puppet/util/yaml.rb +1 -1
- data/lib/puppet/version.rb +1 -1
- data/lib/puppet/x509/cert_provider.rb +9 -5
- data/locales/puppet.pot +640 -521
- data/man/man5/puppet.conf.5 +88 -9
- data/man/man8/puppet-agent.8 +6 -6
- data/man/man8/puppet-apply.8 +1 -1
- data/man/man8/puppet-catalog.8 +1 -1
- data/man/man8/puppet-config.8 +1 -1
- data/man/man8/puppet-describe.8 +1 -1
- data/man/man8/puppet-device.8 +2 -2
- data/man/man8/puppet-doc.8 +1 -1
- data/man/man8/puppet-epp.8 +1 -1
- data/man/man8/puppet-facts.8 +1 -1
- data/man/man8/puppet-filebucket.8 +17 -2
- data/man/man8/puppet-generate.8 +1 -1
- data/man/man8/puppet-help.8 +6 -3
- data/man/man8/puppet-key.8 +1 -1
- data/man/man8/puppet-lookup.8 +1 -1
- data/man/man8/puppet-man.8 +1 -1
- data/man/man8/puppet-module.8 +4 -1
- data/man/man8/puppet-node.8 +1 -1
- data/man/man8/puppet-parser.8 +1 -1
- data/man/man8/puppet-plugin.8 +1 -1
- data/man/man8/puppet-report.8 +1 -1
- data/man/man8/puppet-resource.8 +1 -1
- data/man/man8/puppet-script.8 +1 -1
- data/man/man8/puppet-ssl.8 +2 -2
- data/man/man8/puppet-status.8 +1 -1
- data/man/man8/puppet.8 +2 -2
- data/spec/fixtures/ssl/unknown-127.0.0.1-key.pem +67 -0
- data/spec/fixtures/ssl/unknown-127.0.0.1.pem +48 -0
- data/spec/fixtures/ssl/unknown-ca-key.pem +67 -0
- data/spec/fixtures/ssl/unknown-ca.pem +59 -0
- data/spec/fixtures/unit/forge/bacula.json +76 -0
- data/spec/fixtures/unit/provider/package/dnfmodule/{dnf-module-list-installed.txt → dnf-module-list.txt} +8 -0
- data/spec/fixtures/unit/provider/package/pkgng/pkg.version +2 -0
- data/spec/fixtures/unit/provider/package/yum/yum-check-update-subscription-manager.txt +9 -0
- data/spec/fixtures/unit/provider/package/zypper/zypper-search-uninstalled.out +13 -0
- data/spec/fixtures/unit/provider/service/systemd/list_unit_files_services +9 -0
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_md5/should_fetch_if_not_on_the_local_disk.yml +1 -102
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_md5/should_not_update_if_content_on_disk_is_up-to-date.yml +1 -106
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_md5/should_update_if_content_differs_on_disk.yml +1 -106
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_mtime/should_fetch_if_mtime_is_older_on_disk.yml +1 -102
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_mtime/should_fetch_if_no_header_specified.yml +1 -98
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_mtime/should_fetch_if_not_on_the_local_disk.yml +1 -102
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_mtime/should_not_update_if_mtime_is_newer_on_disk.yml +1 -102
- data/spec/integration/application/agent_spec.rb +394 -0
- data/spec/integration/application/apply_spec.rb +132 -3
- data/spec/integration/application/filebucket_spec.rb +190 -0
- data/spec/integration/application/plugin_spec.rb +73 -0
- data/spec/integration/configurer_spec.rb +26 -7
- data/spec/integration/http/client_spec.rb +154 -0
- data/spec/integration/indirector/facts/facter_spec.rb +4 -0
- data/spec/integration/indirector/report/yaml.rb +83 -0
- data/spec/integration/module_tool/forge_spec.rb +51 -0
- data/spec/integration/network/http_pool_spec.rb +76 -20
- data/spec/integration/node/environment_spec.rb +15 -0
- data/spec/integration/util/windows/adsi_spec.rb +6 -1
- data/spec/lib/puppet/test_ca.rb +2 -2
- data/spec/lib/puppet_spec/https.rb +20 -9
- data/spec/lib/puppet_spec/puppetserver.rb +119 -0
- data/spec/shared_contexts/https.rb +29 -0
- data/spec/spec_helper.rb +6 -2
- data/spec/unit/agent_spec.rb +80 -26
- data/spec/unit/application/agent_spec.rb +9 -5
- data/spec/unit/application/apply_spec.rb +2 -12
- data/spec/unit/application/describe_spec.rb +88 -50
- data/spec/unit/application/device_spec.rb +2 -2
- data/spec/unit/application/filebucket_spec.rb +22 -2
- data/spec/unit/application/resource_spec.rb +2 -2
- data/spec/unit/concurrent/lock_spec.rb +29 -0
- data/spec/unit/configurer/fact_handler_spec.rb +0 -4
- data/spec/unit/configurer/plugin_handler_spec.rb +36 -19
- data/spec/unit/configurer_spec.rb +400 -406
- data/spec/unit/context/trusted_information_spec.rb +17 -0
- data/spec/unit/daemon_spec.rb +5 -64
- data/spec/unit/defaults_spec.rb +38 -4
- data/spec/unit/environments_spec.rb +65 -28
- data/spec/unit/face/facts_spec.rb +24 -20
- data/spec/unit/face/module/search_spec.rb +17 -0
- data/spec/unit/face/plugin_spec.rb +12 -10
- data/spec/unit/file_system/uniquefile_spec.rb +11 -0
- data/spec/unit/file_system_spec.rb +26 -2
- data/spec/unit/forge/errors_spec.rb +1 -1
- data/spec/unit/forge/forge_spec.rb +12 -54
- data/spec/unit/forge/module_release_spec.rb +19 -6
- data/spec/unit/forge/repository_spec.rb +63 -157
- data/spec/unit/forge_spec.rb +46 -116
- data/spec/unit/functions/find_template_spec.rb +69 -0
- data/spec/unit/functions/lookup_spec.rb +13 -0
- data/spec/unit/http/client_spec.rb +395 -27
- data/spec/unit/http/external_client_spec.rb +201 -0
- data/spec/unit/http/resolver_spec.rb +81 -12
- data/spec/unit/http/response_spec.rb +69 -0
- data/spec/unit/http/service/ca_spec.rb +100 -7
- data/spec/unit/http/service/compiler_spec.rb +627 -0
- data/spec/unit/http/service/file_server_spec.rb +308 -0
- data/spec/unit/http/service/report_spec.rb +118 -0
- data/spec/unit/http/service_spec.rb +117 -4
- data/spec/unit/http/session_spec.rb +237 -19
- data/spec/unit/indirector/catalog/compiler_spec.rb +47 -29
- data/spec/unit/indirector/catalog/rest_spec.rb +59 -2
- data/spec/unit/indirector/facts/rest_spec.rb +79 -24
- data/spec/unit/indirector/file_bucket_file/rest_spec.rb +82 -2
- data/spec/unit/indirector/file_content/rest_spec.rb +53 -2
- data/spec/unit/indirector/file_metadata/http_spec.rb +167 -0
- data/spec/unit/indirector/file_metadata/rest_spec.rb +110 -2
- data/spec/unit/indirector/node/rest_spec.rb +57 -2
- data/spec/unit/indirector/report/rest_spec.rb +58 -51
- data/spec/unit/indirector/resource/ral_spec.rb +7 -8
- data/spec/unit/indirector/rest_spec.rb +13 -0
- data/spec/unit/indirector/status/rest_spec.rb +43 -2
- data/spec/unit/network/http/connection_spec.rb +549 -176
- data/spec/unit/network/http/nocache_pool_spec.rb +25 -3
- data/spec/unit/network/http/pool_spec.rb +89 -11
- data/spec/unit/network/http_pool_spec.rb +63 -57
- data/spec/unit/network/http_spec.rb +1 -1
- data/spec/unit/node/environment_spec.rb +16 -0
- data/spec/unit/node/facts_spec.rb +2 -1
- data/spec/unit/node_spec.rb +7 -4
- data/spec/unit/pops/evaluator/evaluating_parser_spec.rb +8 -3
- data/spec/unit/pops/serialization/to_from_hr_spec.rb +6 -1
- data/spec/unit/pops/validator/validator_spec.rb +7 -2
- data/spec/unit/provider/aix_object_spec.rb +16 -2
- data/spec/unit/provider/group/groupadd_spec.rb +181 -56
- data/spec/unit/provider/group/windows_adsi_spec.rb +43 -10
- data/spec/unit/provider/package/aix_spec.rb +29 -0
- data/spec/unit/provider/package/apt_spec.rb +43 -2
- data/spec/unit/provider/package/aptitude_spec.rb +1 -0
- data/spec/unit/provider/package/dnfmodule_spec.rb +76 -15
- data/spec/unit/provider/package/dpkg_spec.rb +28 -6
- data/spec/unit/provider/package/gem_spec.rb +40 -0
- data/spec/unit/provider/package/openbsd_spec.rb +17 -0
- data/spec/unit/provider/package/pacman_spec.rb +6 -21
- data/spec/unit/provider/package/pip_spec.rb +68 -19
- data/spec/unit/provider/package/pkg_spec.rb +15 -1
- data/spec/unit/provider/package/pkgdmg_spec.rb +1 -1
- data/spec/unit/provider/package/pkgng_spec.rb +38 -0
- data/spec/unit/provider/package/portage_spec.rb +9 -4
- data/spec/unit/provider/package/puppet_gem_spec.rb +8 -0
- data/spec/unit/provider/package/rpm_spec.rb +0 -212
- data/spec/unit/provider/package/yum_spec.rb +292 -0
- data/spec/unit/provider/package/zypper_spec.rb +84 -0
- data/spec/unit/provider/package_targetable_spec.rb +60 -0
- data/spec/unit/provider/service/init_spec.rb +1 -0
- data/spec/unit/provider/service/openbsd_spec.rb +9 -0
- data/spec/unit/provider/service/openwrt_spec.rb +1 -0
- data/spec/unit/provider/service/redhat_spec.rb +9 -0
- data/spec/unit/provider/service/systemd_spec.rb +92 -12
- data/spec/unit/provider/user/directoryservice_spec.rb +41 -0
- data/spec/unit/provider/user/hpux_spec.rb +2 -2
- data/spec/unit/provider/user/useradd_spec.rb +21 -8
- data/spec/unit/provider/user/windows_adsi_spec.rb +3 -3
- data/spec/unit/puppet_pal_2pec.rb +0 -26
- data/spec/unit/puppet_pal_catalog_spec.rb +46 -0
- data/spec/unit/puppet_spec.rb +47 -0
- data/spec/unit/reports/http_spec.rb +70 -52
- data/spec/unit/settings/autosign_setting_spec.rb +1 -1
- data/spec/unit/settings/http_extra_headers_spec.rb +64 -0
- data/spec/unit/ssl/certificate_spec.rb +7 -0
- data/spec/unit/ssl/host_spec.rb +4 -2
- data/spec/unit/ssl/oids_spec.rb +1 -0
- data/spec/unit/ssl/ssl_provider_spec.rb +71 -0
- data/spec/unit/ssl/state_machine_spec.rb +99 -13
- data/spec/unit/transaction/persistence_spec.rb +1 -10
- data/spec/unit/transaction/report_spec.rb +4 -0
- data/spec/unit/transaction_spec.rb +45 -1
- data/spec/unit/type/file/content_spec.rb +9 -3
- data/spec/unit/type/file/ensure_spec.rb +1 -2
- data/spec/unit/type/file/source_spec.rb +86 -35
- data/spec/unit/type/package_spec.rb +8 -0
- data/spec/unit/type/service_spec.rb +9 -8
- data/spec/unit/type/user_spec.rb +1 -2
- data/spec/unit/util/at_fork_spec.rb +3 -2
- data/spec/unit/util/autoload_spec.rb +2 -1
- data/spec/unit/util/log/destinations_spec.rb +1 -29
- data/spec/unit/util/log_spec.rb +0 -138
- data/spec/unit/util/logging_spec.rb +200 -0
- data/spec/unit/util/package/version/debian_spec.rb +83 -0
- data/spec/unit/util/package/version/pip_spec.rb +464 -0
- data/spec/unit/util/package/version/range_spec.rb +175 -0
- data/spec/unit/util/package/version/rpm_spec.rb +121 -0
- data/spec/unit/util/pidlock_spec.rb +112 -42
- data/spec/unit/util/plist_spec.rb +20 -0
- data/spec/unit/util/rpm_compare_spec.rb +196 -0
- data/spec/unit/util/storage_spec.rb +1 -8
- data/spec/unit/util/windows/adsi_spec.rb +55 -4
- data/spec/unit/util/windows/sid_spec.rb +2 -2
- data/spec/unit/x509/cert_provider_spec.rb +24 -4
- data/tasks/generate_cert_fixtures.rake +15 -1
- data/tasks/manpages.rake +6 -35
- metadata +92 -12
- data/COMMITTERS.md +0 -244
- data/spec/integration/faces/plugin_spec.rb +0 -61
- data/spec/lib/puppet_spec/validators.rb +0 -37
| @@ -14,14 +14,6 @@ describe Puppet::Application::Apply do | |
| 14 14 | 
             
                Puppet[:reports] = "none"
         | 
| 15 15 | 
             
              end
         | 
| 16 16 |  | 
| 17 | 
            -
              after :each do
         | 
| 18 | 
            -
                Puppet::Node::Facts.indirection.reset_terminus_class
         | 
| 19 | 
            -
                Puppet::Node::Facts.indirection.cache_class = nil
         | 
| 20 | 
            -
             | 
| 21 | 
            -
                Puppet::Node.indirection.reset_terminus_class
         | 
| 22 | 
            -
                Puppet::Node.indirection.cache_class = nil
         | 
| 23 | 
            -
              end
         | 
| 24 | 
            -
             | 
| 25 17 | 
             
              [:debug,:loadclasses,:test,:verbose,:use_nodes,:detailed_exitcodes,:catalog, :write_catalog_summary].each do |option|
         | 
| 26 18 | 
             
                it "should declare handle_#{option} method" do
         | 
| 27 19 | 
             
                  expect(@apply).to respond_to("handle_#{option}".to_sym)
         | 
| @@ -182,13 +174,11 @@ describe Puppet::Application::Apply do | |
| 182 174 | 
             
                    Puppet[:prerun_command] = ''
         | 
| 183 175 | 
             
                    Puppet[:postrun_command] = ''
         | 
| 184 176 |  | 
| 185 | 
            -
                    Puppet::Node::Facts.indirection.terminus_class = :memory
         | 
| 186 | 
            -
                    Puppet::Node::Facts.indirection.cache_class = :memory
         | 
| 187 177 | 
             
                    Puppet::Node.indirection.terminus_class = :memory
         | 
| 188 178 | 
             
                    Puppet::Node.indirection.cache_class = :memory
         | 
| 189 179 |  | 
| 190 | 
            -
                     | 
| 191 | 
            -
                    Puppet::Node::Facts.indirection.save( | 
| 180 | 
            +
                    facts = Puppet::Node::Facts.new(Puppet[:node_name_value])
         | 
| 181 | 
            +
                    Puppet::Node::Facts.indirection.save(facts)
         | 
| 192 182 |  | 
| 193 183 | 
             
                    @node = Puppet::Node.new(Puppet[:node_name_value])
         | 
| 194 184 | 
             
                    Puppet::Node.indirection.save(@node)
         | 
| @@ -3,95 +3,133 @@ require 'spec_helper' | |
| 3 3 | 
             
            require 'puppet/application/describe'
         | 
| 4 4 |  | 
| 5 5 | 
             
            describe Puppet::Application::Describe do
         | 
| 6 | 
            -
               | 
| 7 | 
            -
             | 
| 8 | 
            -
               | 
| 6 | 
            +
              let(:describe) { Puppet::Application[:describe] }
         | 
| 7 | 
            +
             | 
| 8 | 
            +
              it "lists all types" do
         | 
| 9 | 
            +
                describe.command_line.args << '--list'
         | 
| 9 10 |  | 
| 10 | 
            -
             | 
| 11 | 
            -
             | 
| 11 | 
            +
                expect {
         | 
| 12 | 
            +
                  describe.run
         | 
| 13 | 
            +
                }.to output(/These are the types known to puppet:/).to_stdout
         | 
| 12 14 | 
             
              end
         | 
| 13 15 |  | 
| 14 | 
            -
              it " | 
| 15 | 
            -
                 | 
| 16 | 
            +
              it "describes a single type" do
         | 
| 17 | 
            +
                describe.command_line.args << 'exec'
         | 
| 18 | 
            +
             | 
| 19 | 
            +
                expect {
         | 
| 20 | 
            +
                  describe.run
         | 
| 21 | 
            +
                }.to output(/exec.*====.*Executes external commands/m).to_stdout
         | 
| 16 22 | 
             
              end
         | 
| 17 23 |  | 
| 18 | 
            -
               | 
| 19 | 
            -
                 | 
| 20 | 
            -
                  expect(@describe).to respond_to("handle_#{option}".to_sym)
         | 
| 21 | 
            -
                end
         | 
| 24 | 
            +
              it "describes multiple types" do
         | 
| 25 | 
            +
                describe.command_line.args.concat(['exec', 'file'])
         | 
| 22 26 |  | 
| 23 | 
            -
                 | 
| 24 | 
            -
                   | 
| 25 | 
            -
             | 
| 26 | 
            -
                end
         | 
| 27 | 
            +
                expect {
         | 
| 28 | 
            +
                  describe.run
         | 
| 29 | 
            +
                }.to output(/Executes external commands.*Manages files, including their content, ownership, and permissions./m).to_stdout
         | 
| 27 30 | 
             
              end
         | 
| 28 31 |  | 
| 32 | 
            +
              it "describes parameters for the type by default" do
         | 
| 33 | 
            +
                describe.command_line.args << 'exec'
         | 
| 29 34 |  | 
| 30 | 
            -
             | 
| 31 | 
            -
             | 
| 32 | 
            -
             | 
| 35 | 
            +
                expect {
         | 
| 36 | 
            +
                  describe.run
         | 
| 37 | 
            +
                }.to output(/Parameters\n----------/m).to_stdout
         | 
| 38 | 
            +
              end
         | 
| 33 39 |  | 
| 34 | 
            -
             | 
| 35 | 
            -
                 | 
| 40 | 
            +
              it "lists parameter names, but excludes description in short mode" do
         | 
| 41 | 
            +
                describe.command_line.args.concat(['exec', '-s'])
         | 
| 42 | 
            +
             | 
| 43 | 
            +
                expect {
         | 
| 44 | 
            +
                  describe.run
         | 
| 45 | 
            +
                }.to output(/Parameters.*command, creates, cwd/m).to_stdout
         | 
| 36 46 | 
             
              end
         | 
| 37 47 |  | 
| 38 | 
            -
               | 
| 39 | 
            -
                 | 
| 40 | 
            -
                  @describe.handle_short(nil)
         | 
| 48 | 
            +
              it "outputs providers for the type" do
         | 
| 49 | 
            +
                describe.command_line.args.concat(['exec', '--providers'])
         | 
| 41 50 |  | 
| 42 | 
            -
             | 
| 43 | 
            -
             | 
| 51 | 
            +
                expect {
         | 
| 52 | 
            +
                  describe.run
         | 
| 53 | 
            +
                }.to output(/Providers.*#{Regexp.escape('**posix**')}.*#{Regexp.escape('**windows**')}/m).to_stdout
         | 
| 44 54 | 
             
              end
         | 
| 45 55 |  | 
| 46 | 
            -
               | 
| 47 | 
            -
                 | 
| 48 | 
            -
                  allow(@describe.command_line).to receive(:args).and_return(['1','2'])
         | 
| 49 | 
            -
                  @describe.setup
         | 
| 56 | 
            +
              it "lists metaparameters for a type" do
         | 
| 57 | 
            +
                describe.command_line.args.concat(['exec', '--meta'])
         | 
| 50 58 |  | 
| 51 | 
            -
             | 
| 52 | 
            -
             | 
| 59 | 
            +
                expect {
         | 
| 60 | 
            +
                  describe.run
         | 
| 61 | 
            +
                }.to output(/Meta Parameters.*#{Regexp.escape('**notify**')}/m).to_stdout
         | 
| 53 62 | 
             
              end
         | 
| 54 63 |  | 
| 55 | 
            -
               | 
| 64 | 
            +
              it "outputs no documentation if the summary is missing" do
         | 
| 65 | 
            +
                Puppet::Type.newtype(:describe_test) {}
         | 
| 66 | 
            +
             | 
| 67 | 
            +
                describe.command_line.args << '--list'
         | 
| 68 | 
            +
                expect {
         | 
| 69 | 
            +
                  describe.run
         | 
| 70 | 
            +
                }.to output(/#{Regexp.escape("describe_test   - .. no documentation ..")}/).to_stdout
         | 
| 71 | 
            +
              end
         | 
| 56 72 |  | 
| 57 | 
            -
             | 
| 58 | 
            -
             | 
| 59 | 
            -
                   | 
| 73 | 
            +
              it "outputs the first short sentence ending in a dot" do
         | 
| 74 | 
            +
                Puppet::Type.newtype(:describe_test) do
         | 
| 75 | 
            +
                  @doc = "ends in a dot."
         | 
| 60 76 | 
             
                end
         | 
| 61 77 |  | 
| 62 | 
            -
                 | 
| 63 | 
            -
             | 
| 78 | 
            +
                describe.command_line.args << '--list'
         | 
| 79 | 
            +
                expect {
         | 
| 80 | 
            +
                  describe.run
         | 
| 81 | 
            +
                }.to output(/#{Regexp.escape("describe_test   - ends in a dot\n")}/).to_stdout
         | 
| 82 | 
            +
              end
         | 
| 64 83 |  | 
| 65 | 
            -
             | 
| 84 | 
            +
              it "outputs the first short sentence missing a dot" do
         | 
| 85 | 
            +
                Puppet::Type.newtype(:describe_test) do
         | 
| 86 | 
            +
                  @doc = "missing a dot"
         | 
| 87 | 
            +
                end
         | 
| 66 88 |  | 
| 67 | 
            -
             | 
| 89 | 
            +
                describe.command_line.args << '--list'
         | 
| 90 | 
            +
                expect {
         | 
| 91 | 
            +
                  describe.run
         | 
| 92 | 
            +
                }.to output(/describe_test   - missing a dot\n/).to_stdout
         | 
| 93 | 
            +
              end
         | 
| 94 | 
            +
             | 
| 95 | 
            +
              it "truncates long summaries ending in a dot" do
         | 
| 96 | 
            +
                Puppet::Type.newtype(:describe_test) do
         | 
| 97 | 
            +
                  @doc = "This sentence is more than 45 characters and ends in a dot."
         | 
| 68 98 | 
             
                end
         | 
| 69 99 |  | 
| 70 | 
            -
                 | 
| 71 | 
            -
             | 
| 72 | 
            -
                   | 
| 100 | 
            +
                describe.command_line.args << '--list'
         | 
| 101 | 
            +
                expect {
         | 
| 102 | 
            +
                  describe.run
         | 
| 103 | 
            +
                }.to output(/#{Regexp.escape("describe_test   - This sentence is more than 45 characters and  ...")}/).to_stdout
         | 
| 104 | 
            +
              end
         | 
| 73 105 |  | 
| 74 | 
            -
             | 
| 75 | 
            -
             | 
| 106 | 
            +
              it "truncates long summaries missing a dot" do
         | 
| 107 | 
            +
                Puppet::Type.newtype(:describe_test) do
         | 
| 108 | 
            +
                  @doc = "This sentence is more than 45 characters and is missing a dot"
         | 
| 76 109 | 
             
                end
         | 
| 110 | 
            +
             | 
| 111 | 
            +
                describe.command_line.args << '--list'
         | 
| 112 | 
            +
                expect {
         | 
| 113 | 
            +
                  describe.run
         | 
| 114 | 
            +
                }.to output(/#{Regexp.escape("describe_test   - This sentence is more than 45 characters and  ...")}/).to_stdout
         | 
| 77 115 | 
             
              end
         | 
| 78 116 |  | 
| 79 | 
            -
              it " | 
| 80 | 
            -
                 | 
| 117 | 
            +
              it "formats text with long non-space runs without garbling" do
         | 
| 118 | 
            +
                f = Formatter.new(76)
         | 
| 81 119 |  | 
| 82 | 
            -
                 | 
| 120 | 
            +
                teststring = <<TESTSTRING
         | 
| 83 121 | 
             
            . 12345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890 nick@magpie.puppetlabs.lan
         | 
| 84 122 | 
             
            **this part should not repeat!**
         | 
| 85 123 | 
             
            TESTSTRING
         | 
| 86 124 |  | 
| 87 | 
            -
                 | 
| 125 | 
            +
                expected_result = <<EXPECTED
         | 
| 88 126 | 
             
            .
         | 
| 89 127 | 
             
            1234567890123456789012345678901234567890123456789012345678901234567890123456
         | 
| 90 128 | 
             
            7890123456789012345678901234567890 nick@magpie.puppetlabs.lan
         | 
| 91 129 | 
             
            **this part should not repeat!**
         | 
| 92 130 | 
             
            EXPECTED
         | 
| 93 131 |  | 
| 94 | 
            -
                result =  | 
| 95 | 
            -
                expect(result).to eql( | 
| 132 | 
            +
                result = f.wrap(teststring, {:indent => 0, :scrub => true})
         | 
| 133 | 
            +
                expect(result).to eql(expected_result)
         | 
| 96 134 | 
             
              end
         | 
| 97 135 | 
             
            end
         | 
| @@ -459,7 +459,7 @@ describe Puppet::Application::Device do | |
| 459 459 | 
             
                      resource = Puppet::Type.type(:user).new(:name => "jim").to_resource
         | 
| 460 460 | 
             
                      allow(device.command_line).to receive(:args).and_return(['user', 'jim'])
         | 
| 461 461 | 
             
                      expect(Puppet::Resource.indirection).to receive(:find).with('user/jim').and_return(resource)
         | 
| 462 | 
            -
                      expect(device).to receive(:puts).with("user { 'jim':\n}")
         | 
| 462 | 
            +
                      expect(device).to receive(:puts).with("user { 'jim':\n  ensure => 'absent',\n}")
         | 
| 463 463 | 
             
                      expect { device.main }.to exit_with 0
         | 
| 464 464 | 
             
                    end
         | 
| 465 465 |  | 
| @@ -470,7 +470,7 @@ describe Puppet::Application::Device do | |
| 470 470 | 
             
                      allow(device.options).to receive(:[]).with(:to_yaml).and_return(true)
         | 
| 471 471 | 
             
                      allow(device.command_line).to receive(:args).and_return(['user'])
         | 
| 472 472 | 
             
                      expect(Puppet::Resource.indirection).to receive(:search).with('user/', {}).and_return(resources)
         | 
| 473 | 
            -
                      expect(device).to receive(:puts).with("---\nuser:\n  title:  | 
| 473 | 
            +
                      expect(device).to receive(:puts).with("---\nuser:\n  title:\n    ensure: absent\n")
         | 
| 474 474 | 
             
                      expect { device.main }.to exit_with 0
         | 
| 475 475 | 
             
                    end
         | 
| 476 476 | 
             
                  end
         | 
| @@ -114,12 +114,31 @@ describe Puppet::Application::Filebucket do | |
| 114 114 | 
             
                    @filebucket.setup
         | 
| 115 115 | 
             
                  end
         | 
| 116 116 |  | 
| 117 | 
            -
                  it "should default to the first server_list entry if set" do
         | 
| 117 | 
            +
                  it "should default to the first good server_list entry if server_list is set" do
         | 
| 118 | 
            +
                    stub_request(:get, "https://foo:8140/status/v1/simple/master").to_return(status: 200)
         | 
| 118 119 | 
             
                    Puppet[:server_list] = "foo,bar,baz"
         | 
| 119 120 | 
             
                    expect(Puppet::FileBucket::Dipper).to receive(:new).with(hash_including(Server: "foo"))
         | 
| 120 121 | 
             
                    @filebucket.setup
         | 
| 121 122 | 
             
                  end
         | 
| 122 123 |  | 
| 124 | 
            +
                  it "should walk server_list until it finds a good entry" do
         | 
| 125 | 
            +
                    stub_request(:get, "https://foo:8140/status/v1/simple/master").to_return(status: 502)
         | 
| 126 | 
            +
                    stub_request(:get, "https://bar:8140/status/v1/simple/master").to_return(status: 200)
         | 
| 127 | 
            +
                    Puppet[:server_list] = "foo,bar,baz"
         | 
| 128 | 
            +
                    expect(Puppet::FileBucket::Dipper).to receive(:new).with(hash_including(Server: "bar"))
         | 
| 129 | 
            +
                    @filebucket.setup
         | 
| 130 | 
            +
                  end
         | 
| 131 | 
            +
             | 
| 132 | 
            +
                  # FileBucket catches any exceptions raised, logs them, then just exits
         | 
| 133 | 
            +
                  it "raises an error if there are no functional servers in server_list" do
         | 
| 134 | 
            +
                    stub_request(:get, "https://foo:8140/status/v1/simple/master").to_return(status: 404)
         | 
| 135 | 
            +
                    stub_request(:get, "https://bar:8140/status/v1/simple/master").to_return(status: 404)
         | 
| 136 | 
            +
                    Puppet[:server] = 'horacio'
         | 
| 137 | 
            +
                    Puppet[:server_list] = "foo,bar"
         | 
| 138 | 
            +
             | 
| 139 | 
            +
                    expect{@filebucket.setup}.to exit_with(1)
         | 
| 140 | 
            +
                  end
         | 
| 141 | 
            +
             | 
| 123 142 | 
             
                  it "should fall back to server if server_list is empty" do
         | 
| 124 143 | 
             
                    Puppet[:server_list] = ""
         | 
| 125 144 | 
             
                    expect(Puppet::FileBucket::Dipper).to receive(:new).with(hash_including(Server: "puppet"))
         | 
| @@ -127,8 +146,9 @@ describe Puppet::Application::Filebucket do | |
| 127 146 | 
             
                  end
         | 
| 128 147 |  | 
| 129 148 | 
             
                  it "should take both the server and port specified in server_list" do
         | 
| 149 | 
            +
                    stub_request(:get, "https://foo:632/status/v1/simple/master").to_return(status: 200)
         | 
| 130 150 | 
             
                    Puppet[:server_list] = "foo:632,bar:6215,baz:351"
         | 
| 131 | 
            -
                    expect(Puppet::FileBucket::Dipper).to receive(:new).with({ :Server => "foo", :Port =>  | 
| 151 | 
            +
                    expect(Puppet::FileBucket::Dipper).to receive(:new).with({ :Server => "foo", :Port => 632 })
         | 
| 132 152 | 
             
                    @filebucket.setup
         | 
| 133 153 | 
             
                  end
         | 
| 134 154 | 
             
                end
         | 
| @@ -12,9 +12,9 @@ describe Puppet::Application::Resource do | |
| 12 12 | 
             
              end
         | 
| 13 13 |  | 
| 14 14 | 
             
              describe "in preinit" do
         | 
| 15 | 
            -
                it "should  | 
| 15 | 
            +
                it "should include provider parameter by default" do
         | 
| 16 16 | 
             
                  @resource_app.preinit
         | 
| 17 | 
            -
                  expect(@resource_app.extra_params).to eq([])
         | 
| 17 | 
            +
                  expect(@resource_app.extra_params).to eq([:provider])
         | 
| 18 18 | 
             
                end
         | 
| 19 19 | 
             
              end
         | 
| 20 20 |  | 
| @@ -0,0 +1,29 @@ | |
| 1 | 
            +
            require 'spec_helper'
         | 
| 2 | 
            +
            require 'puppet/concurrent/lock'
         | 
| 3 | 
            +
             | 
| 4 | 
            +
            describe Puppet::Concurrent::Lock do
         | 
| 5 | 
            +
              if Puppet::Util::Platform.jruby?
         | 
| 6 | 
            +
                context 'on jruby' do
         | 
| 7 | 
            +
                  it 'synchronizes a block on itself' do
         | 
| 8 | 
            +
                    iterations = 100
         | 
| 9 | 
            +
                    value = 0
         | 
| 10 | 
            +
             | 
| 11 | 
            +
                    lock = Puppet::Concurrent::Lock.new
         | 
| 12 | 
            +
                    threads = iterations.times.collect do
         | 
| 13 | 
            +
                      Thread.new do
         | 
| 14 | 
            +
                        lock.synchronize do
         | 
| 15 | 
            +
                          tmp = (value += 1)
         | 
| 16 | 
            +
                          sleep(0.001)
         | 
| 17 | 
            +
                          # This update using tmp is designed to lose increments if threads overlap
         | 
| 18 | 
            +
                          value = tmp + 1
         | 
| 19 | 
            +
                        end
         | 
| 20 | 
            +
                      end
         | 
| 21 | 
            +
                    end
         | 
| 22 | 
            +
                    threads.each(&:join)
         | 
| 23 | 
            +
             | 
| 24 | 
            +
                    # In my testing this always fails by quite a lot when not synchronized (ie on mri)
         | 
| 25 | 
            +
                    expect(value).to eq(iterations * 2)
         | 
| 26 | 
            +
                  end
         | 
| 27 | 
            +
                end
         | 
| 28 | 
            +
              end
         | 
| 29 | 
            +
            end
         | 
| @@ -22,10 +22,6 @@ describe Puppet::Configurer::FactHandler do | |
| 22 22 |  | 
| 23 23 | 
             
              let(:facthandler) { FactHandlerTester.new('production') }
         | 
| 24 24 |  | 
| 25 | 
            -
              before :each do
         | 
| 26 | 
            -
                Puppet::Node::Facts.indirection.terminus_class = :memory
         | 
| 27 | 
            -
              end
         | 
| 28 | 
            -
             | 
| 29 25 | 
             
              describe "when finding facts" do
         | 
| 30 26 | 
             
                it "should use the node name value to retrieve the facts" do
         | 
| 31 27 | 
             
                  foo_facts = Puppet::Node::Facts.new('foo')
         | 
| @@ -6,13 +6,17 @@ describe Puppet::Configurer::PluginHandler do | |
| 6 6 | 
             
              let(:pluginhandler) { Puppet::Configurer::PluginHandler.new() }
         | 
| 7 7 | 
             
              let(:environment)   { Puppet::Node::Environment.create(:myenv, []) }
         | 
| 8 8 |  | 
| 9 | 
            +
              before :each do
         | 
| 10 | 
            +
                # PluginHandler#load_plugin has an extra-strong rescue clause
         | 
| 11 | 
            +
                # this mock is to make sure that we don't silently ignore errors
         | 
| 12 | 
            +
                expect(Puppet).not_to receive(:err)
         | 
| 13 | 
            +
              end
         | 
| 14 | 
            +
             | 
| 9 15 | 
             
              context "server agent version is 5.3.4" do
         | 
| 10 | 
            -
                 | 
| 11 | 
            -
                   | 
| 12 | 
            -
             | 
| 13 | 
            -
                   | 
| 14 | 
            -
                  # Server_agent version needs to be at 5.3.4 in order to mount locales
         | 
| 15 | 
            -
                  Puppet.push_context({:server_agent_version => "5.3.4"})
         | 
| 16 | 
            +
                around do |example|
         | 
| 17 | 
            +
                  Puppet.override(server_agent_version: "5.3.4") do
         | 
| 18 | 
            +
                    example.run
         | 
| 19 | 
            +
                  end
         | 
| 16 20 | 
             
                end
         | 
| 17 21 |  | 
| 18 22 | 
             
                it "downloads plugins, facts, and locales" do
         | 
| @@ -43,12 +47,10 @@ describe Puppet::Configurer::PluginHandler do | |
| 43 47 | 
             
              end
         | 
| 44 48 |  | 
| 45 49 | 
             
              context "server agent version is 5.3.3" do
         | 
| 46 | 
            -
                 | 
| 47 | 
            -
                   | 
| 48 | 
            -
             | 
| 49 | 
            -
                   | 
| 50 | 
            -
                  # Server_agent version needs to be at 5.3.4 in order to mount locales
         | 
| 51 | 
            -
                  Puppet.push_context({:server_agent_version => "5.3.3"})
         | 
| 50 | 
            +
                around do |example|
         | 
| 51 | 
            +
                  Puppet.override(server_agent_version: "5.3.3") do
         | 
| 52 | 
            +
                    example.run
         | 
| 53 | 
            +
                  end
         | 
| 52 54 | 
             
                end
         | 
| 53 55 |  | 
| 54 56 | 
             
                it "returns downloaded plugin, fact, but not locale filenames" do
         | 
| @@ -69,15 +71,30 @@ describe Puppet::Configurer::PluginHandler do | |
| 69 71 | 
             
              end
         | 
| 70 72 |  | 
| 71 73 | 
             
              context "blank server agent version" do
         | 
| 72 | 
            -
                 | 
| 73 | 
            -
                   | 
| 74 | 
            -
             | 
| 75 | 
            -
                   | 
| 76 | 
            -
             | 
| 77 | 
            -
             | 
| 78 | 
            -
             | 
| 74 | 
            +
                around do |example|
         | 
| 75 | 
            +
                  Puppet.override(server_agent_version: "") do
         | 
| 76 | 
            +
                    example.run
         | 
| 77 | 
            +
                  end
         | 
| 78 | 
            +
                end
         | 
| 79 | 
            +
             | 
| 80 | 
            +
                it "returns downloaded plugin, fact, but not locale filenames" do
         | 
| 81 | 
            +
                  times_called = 0
         | 
| 82 | 
            +
                  allow_any_instance_of(Puppet::Configurer::Downloader).to receive(:evaluate) do
         | 
| 83 | 
            +
                    times_called += 1
         | 
| 84 | 
            +
             | 
| 85 | 
            +
                    if times_called == 1
         | 
| 86 | 
            +
                      %w[/a]
         | 
| 87 | 
            +
                    else
         | 
| 88 | 
            +
                      %w[/b]
         | 
| 89 | 
            +
                    end
         | 
| 90 | 
            +
                  end
         | 
| 91 | 
            +
             | 
| 92 | 
            +
                  expect(pluginhandler.download_plugins(environment)).to match_array(%w[/a /b])
         | 
| 93 | 
            +
                  expect(times_called).to eq(2)
         | 
| 79 94 | 
             
                end
         | 
| 95 | 
            +
              end
         | 
| 80 96 |  | 
| 97 | 
            +
              context "nil server agent version" do
         | 
| 81 98 | 
             
                it "returns downloaded plugin, fact, but not locale filenames" do
         | 
| 82 99 | 
             
                  times_called = 0
         | 
| 83 100 | 
             
                  allow_any_instance_of(Puppet::Configurer::Downloader).to receive(:evaluate) do
         | 
| @@ -1,108 +1,88 @@ | |
| 1 1 | 
             
            require 'spec_helper'
         | 
| 2 2 | 
             
            require 'puppet/configurer'
         | 
| 3 | 
            +
            require 'webmock/rspec'
         | 
| 3 4 |  | 
| 4 5 | 
             
            describe Puppet::Configurer do
         | 
| 5 6 | 
             
              before do
         | 
| 6 | 
            -
                allow(Puppet.settings).to receive(:use).and_return(true)
         | 
| 7 | 
            -
                @agent = Puppet::Configurer.new
         | 
| 8 | 
            -
                allow(@agent).to receive(:init_storage)
         | 
| 9 | 
            -
                allow(Puppet::Util::Storage).to receive(:store)
         | 
| 10 7 | 
             
                Puppet[:server] = "puppetmaster"
         | 
| 11 8 | 
             
                Puppet[:report] = true
         | 
| 12 | 
            -
              end
         | 
| 13 9 |  | 
| 14 | 
            -
             | 
| 15 | 
            -
                expect(Puppet::Configurer.ancestors).to be_include(Puppet::Configurer::FactHandler)
         | 
| 10 | 
            +
                catalog.add_resource(resource)
         | 
| 16 11 | 
             
              end
         | 
| 17 12 |  | 
| 13 | 
            +
              let(:node_name) { Puppet[:node_name_value] }
         | 
| 14 | 
            +
              let(:configurer) { Puppet::Configurer.new }
         | 
| 15 | 
            +
              let(:report) { Puppet::Transaction::Report.new }
         | 
| 16 | 
            +
              let(:catalog) { Puppet::Resource::Catalog.new(node_name, Puppet::Node::Environment.remote(Puppet[:environment].to_sym)) }
         | 
| 17 | 
            +
              let(:resource) { Puppet::Resource.new(:notice, 'a') }
         | 
| 18 | 
            +
              let(:facts) { Puppet::Node::Facts.new(node_name) }
         | 
| 19 | 
            +
             | 
| 18 20 | 
             
              describe "when executing a pre-run hook" do
         | 
| 19 21 | 
             
                it "should do nothing if the hook is set to an empty string" do
         | 
| 20 22 | 
             
                  Puppet.settings[:prerun_command] = ""
         | 
| 21 | 
            -
                  expect(Puppet::Util).not_to receive(: | 
| 23 | 
            +
                  expect(Puppet::Util::Execution).not_to receive(:execute)
         | 
| 22 24 |  | 
| 23 | 
            -
                   | 
| 25 | 
            +
                  configurer.execute_prerun_command
         | 
| 24 26 | 
             
                end
         | 
| 25 27 |  | 
| 26 28 | 
             
                it "should execute any pre-run command provided via the 'prerun_command' setting" do
         | 
| 27 29 | 
             
                  Puppet.settings[:prerun_command] = "/my/command"
         | 
| 28 30 | 
             
                  expect(Puppet::Util::Execution).to receive(:execute).with(["/my/command"]).and_raise(Puppet::ExecutionFailure, "Failed")
         | 
| 29 31 |  | 
| 30 | 
            -
                   | 
| 32 | 
            +
                  configurer.execute_prerun_command
         | 
| 31 33 | 
             
                end
         | 
| 32 34 |  | 
| 33 35 | 
             
                it "should fail if the command fails" do
         | 
| 34 36 | 
             
                  Puppet.settings[:prerun_command] = "/my/command"
         | 
| 35 37 | 
             
                  expect(Puppet::Util::Execution).to receive(:execute).with(["/my/command"]).and_raise(Puppet::ExecutionFailure, "Failed")
         | 
| 36 38 |  | 
| 37 | 
            -
                  expect( | 
| 39 | 
            +
                  expect(configurer.execute_prerun_command).to be_falsey
         | 
| 38 40 | 
             
                end
         | 
| 39 41 | 
             
              end
         | 
| 40 42 |  | 
| 41 43 | 
             
              describe "when executing a post-run hook" do
         | 
| 42 44 | 
             
                it "should do nothing if the hook is set to an empty string" do
         | 
| 43 45 | 
             
                  Puppet.settings[:postrun_command] = ""
         | 
| 44 | 
            -
                  expect(Puppet::Util).not_to receive(: | 
| 46 | 
            +
                  expect(Puppet::Util::Execution).not_to receive(:execute)
         | 
| 45 47 |  | 
| 46 | 
            -
                   | 
| 48 | 
            +
                  configurer.execute_postrun_command
         | 
| 47 49 | 
             
                end
         | 
| 48 50 |  | 
| 49 51 | 
             
                it "should execute any post-run command provided via the 'postrun_command' setting" do
         | 
| 50 52 | 
             
                  Puppet.settings[:postrun_command] = "/my/command"
         | 
| 51 53 | 
             
                  expect(Puppet::Util::Execution).to receive(:execute).with(["/my/command"]).and_raise(Puppet::ExecutionFailure, "Failed")
         | 
| 52 54 |  | 
| 53 | 
            -
                   | 
| 55 | 
            +
                  configurer.execute_postrun_command
         | 
| 54 56 | 
             
                end
         | 
| 55 57 |  | 
| 56 58 | 
             
                it "should fail if the command fails" do
         | 
| 57 59 | 
             
                  Puppet.settings[:postrun_command] = "/my/command"
         | 
| 58 60 | 
             
                  expect(Puppet::Util::Execution).to receive(:execute).with(["/my/command"]).and_raise(Puppet::ExecutionFailure, "Failed")
         | 
| 59 61 |  | 
| 60 | 
            -
                  expect( | 
| 62 | 
            +
                  expect(configurer.execute_postrun_command).to be_falsey
         | 
| 61 63 | 
             
                end
         | 
| 62 64 | 
             
              end
         | 
| 63 65 |  | 
| 64 66 | 
             
              describe "when executing a catalog run" do
         | 
| 65 67 | 
             
                before do
         | 
| 66 | 
            -
                  allow(Puppet.settings).to receive(:use).and_return(true)
         | 
| 67 | 
            -
                  allow(@agent).to receive(:download_plugins)
         | 
| 68 | 
            -
                  Puppet::Node::Facts.indirection.terminus_class = :memory
         | 
| 69 | 
            -
                  @facts = Puppet::Node::Facts.new(Puppet[:node_name_value])
         | 
| 70 | 
            -
                  Puppet::Node::Facts.indirection.save(@facts)
         | 
| 71 | 
            -
             | 
| 72 | 
            -
                  @catalog = Puppet::Resource::Catalog.new("tester", Puppet::Node::Environment.remote(Puppet[:environment].to_sym))
         | 
| 73 | 
            -
                  allow(@catalog).to receive(:to_ral).and_return(@catalog)
         | 
| 74 68 | 
             
                  Puppet::Resource::Catalog.indirection.terminus_class = :rest
         | 
| 75 | 
            -
                  allow(Puppet::Resource::Catalog.indirection).to receive(:find).and_return( | 
| 76 | 
            -
                  allow(@agent).to receive(:send_report)
         | 
| 77 | 
            -
                  allow(@agent).to receive(:save_last_run_summary)
         | 
| 78 | 
            -
             | 
| 79 | 
            -
                  allow(Puppet::Util::Log).to receive(:close_all)
         | 
| 80 | 
            -
                end
         | 
| 81 | 
            -
             | 
| 82 | 
            -
                after :all do
         | 
| 83 | 
            -
                  Puppet::Node::Facts.indirection.reset_terminus_class
         | 
| 84 | 
            -
                  Puppet::Resource::Catalog.indirection.reset_terminus_class
         | 
| 85 | 
            -
                end
         | 
| 86 | 
            -
             | 
| 87 | 
            -
                it "should initialize storage" do
         | 
| 88 | 
            -
                  expect(Puppet::Util::Storage).to receive(:load)
         | 
| 89 | 
            -
                  @agent.run
         | 
| 69 | 
            +
                  allow(Puppet::Resource::Catalog.indirection).to receive(:find).and_return(catalog)
         | 
| 90 70 | 
             
                end
         | 
| 91 71 |  | 
| 92 72 | 
             
                it "downloads plugins when told" do
         | 
| 93 | 
            -
                  expect( | 
| 94 | 
            -
                   | 
| 73 | 
            +
                  expect(configurer).to receive(:download_plugins)
         | 
| 74 | 
            +
                  configurer.run(:pluginsync => true)
         | 
| 95 75 | 
             
                end
         | 
| 96 76 |  | 
| 97 77 | 
             
                it "does not download plugins when told" do
         | 
| 98 | 
            -
                  expect( | 
| 99 | 
            -
                   | 
| 78 | 
            +
                  expect(configurer).not_to receive(:download_plugins)
         | 
| 79 | 
            +
                  configurer.run(:pluginsync => false)
         | 
| 100 80 | 
             
                end
         | 
| 101 81 |  | 
| 102 82 | 
             
                it "should carry on when it can't fetch its node definition" do
         | 
| 103 83 | 
             
                  error = Net::HTTPError.new(400, 'dummy server communication error')
         | 
| 104 84 | 
             
                  expect(Puppet::Node.indirection).to receive(:find).and_raise(error)
         | 
| 105 | 
            -
                  expect( | 
| 85 | 
            +
                  expect(configurer.run).to eq(0)
         | 
| 106 86 | 
             
                end
         | 
| 107 87 |  | 
| 108 88 | 
             
                it "applies a cached catalog when it can't connect to the master" do
         | 
| @@ -110,200 +90,158 @@ describe Puppet::Configurer do | |
| 110 90 |  | 
| 111 91 | 
             
                  expect(Puppet::Node.indirection).to receive(:find).and_raise(error)
         | 
| 112 92 | 
             
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(:ignore_cache => true)).and_raise(error)
         | 
| 113 | 
            -
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(:ignore_terminus => true)).and_return( | 
| 93 | 
            +
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(:ignore_terminus => true)).and_return(catalog)
         | 
| 114 94 |  | 
| 115 | 
            -
                  expect( | 
| 95 | 
            +
                  expect(configurer.run).to eq(0)
         | 
| 116 96 | 
             
                end
         | 
| 117 97 |  | 
| 118 98 | 
             
                it "should initialize a transaction report if one is not provided" do
         | 
| 119 | 
            -
                  report = Puppet::Transaction::Report.new
         | 
| 120 99 | 
             
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 121 100 |  | 
| 122 | 
            -
                   | 
| 101 | 
            +
                  configurer.run
         | 
| 123 102 | 
             
                end
         | 
| 124 103 |  | 
| 125 104 | 
             
                it "should respect node_name_fact when setting the host on a report" do
         | 
| 105 | 
            +
                  Puppet[:node_name_value] = nil
         | 
| 126 106 | 
             
                  Puppet[:node_name_fact] = 'my_name_fact'
         | 
| 127 | 
            -
                   | 
| 107 | 
            +
                  facts.values = {'my_name_fact' => 'node_name_from_fact'}
         | 
| 108 | 
            +
                  Puppet::Node::Facts.indirection.save(facts)
         | 
| 128 109 |  | 
| 129 | 
            -
                  report  | 
| 130 | 
            -
             | 
| 131 | 
            -
                  @agent.run(:report => report)
         | 
| 110 | 
            +
                  configurer.run(:report => report)
         | 
| 132 111 | 
             
                  expect(report.host).to eq('node_name_from_fact')
         | 
| 133 112 | 
             
                end
         | 
| 134 113 |  | 
| 135 | 
            -
                it " | 
| 136 | 
            -
                   | 
| 137 | 
            -
                   | 
| 138 | 
            -
                  expect(@catalog).to receive(:apply).with(hash_including(report: report))
         | 
| 139 | 
            -
             | 
| 140 | 
            -
                  @agent.run
         | 
| 141 | 
            -
                end
         | 
| 142 | 
            -
             | 
| 143 | 
            -
                it "should use the provided report if it was passed one" do
         | 
| 144 | 
            -
                  report = Puppet::Transaction::Report.new
         | 
| 145 | 
            -
                  expect(@catalog).to receive(:apply).with(hash_including(report: report))
         | 
| 146 | 
            -
             | 
| 147 | 
            -
                  @agent.run(:report => report)
         | 
| 148 | 
            -
                end
         | 
| 149 | 
            -
             | 
| 150 | 
            -
                it "should set the report as a log destination" do
         | 
| 151 | 
            -
                  report = Puppet::Transaction::Report.new
         | 
| 152 | 
            -
             | 
| 153 | 
            -
                  expect(report).to receive(:<<).with(instance_of(Puppet::Util::Log)).at_least(:once)
         | 
| 114 | 
            +
                it "creates a new report when applying the catalog" do
         | 
| 115 | 
            +
                  options = {}
         | 
| 116 | 
            +
                  configurer.run(options)
         | 
| 154 117 |  | 
| 155 | 
            -
                   | 
| 118 | 
            +
                  expect(options[:report].metrics['time']['catalog_application']).to be_an_instance_of(Float)
         | 
| 156 119 | 
             
                end
         | 
| 157 120 |  | 
| 158 | 
            -
                it " | 
| 159 | 
            -
                   | 
| 121 | 
            +
                it "uses the provided report when applying the catalog" do
         | 
| 122 | 
            +
                  configurer.run(:report => report)
         | 
| 160 123 |  | 
| 161 | 
            -
                   | 
| 124 | 
            +
                  expect(report.metrics['time']['catalog_application']).to be_an_instance_of(Float)
         | 
| 162 125 | 
             
                end
         | 
| 163 126 |  | 
| 164 127 | 
             
                it "should log a failure and do nothing if no catalog can be retrieved" do
         | 
| 165 | 
            -
                  expect( | 
| 128 | 
            +
                  expect(configurer).to receive(:retrieve_catalog).and_return(nil)
         | 
| 166 129 |  | 
| 167 130 | 
             
                  expect(Puppet).to receive(:err).with("Could not retrieve catalog; skipping run")
         | 
| 168 131 |  | 
| 169 | 
            -
                   | 
| 132 | 
            +
                  configurer.run
         | 
| 170 133 | 
             
                end
         | 
| 171 134 |  | 
| 172 | 
            -
                it " | 
| 173 | 
            -
                  expect( | 
| 135 | 
            +
                it "passes arbitrary options when applying the catalog" do
         | 
| 136 | 
            +
                  expect(catalog).to receive(:apply).with(hash_including(one: true))
         | 
| 174 137 |  | 
| 175 | 
            -
                   | 
| 176 | 
            -
                  @agent.run :one => true
         | 
| 177 | 
            -
                end
         | 
| 178 | 
            -
             | 
| 179 | 
            -
                it "should accept a catalog and use it instead of retrieving a different one" do
         | 
| 180 | 
            -
                  expect(@agent).not_to receive(:retrieve_catalog)
         | 
| 181 | 
            -
             | 
| 182 | 
            -
                  expect(@catalog).to receive(:apply)
         | 
| 183 | 
            -
                  @agent.run :one => true, :catalog => @catalog
         | 
| 138 | 
            +
                  configurer.run(catalog: catalog, one: true)
         | 
| 184 139 | 
             
                end
         | 
| 185 140 |  | 
| 186 141 | 
             
                it "should benchmark how long it takes to apply the catalog" do
         | 
| 187 | 
            -
                   | 
| 188 | 
            -
             | 
| 189 | 
            -
                  expect(@agent).to receive(:retrieve_catalog).and_return(@catalog)
         | 
| 190 | 
            -
             | 
| 191 | 
            -
                  expect(@catalog).not_to receive(:apply) # because we're not yielding
         | 
| 192 | 
            -
                  @agent.run
         | 
| 193 | 
            -
                end
         | 
| 194 | 
            -
             | 
| 195 | 
            -
                it "should execute post-run hooks after the run" do
         | 
| 196 | 
            -
                  expect(@agent).to receive(:execute_postrun_command)
         | 
| 142 | 
            +
                  configurer.run(report: report)
         | 
| 197 143 |  | 
| 198 | 
            -
                   | 
| 144 | 
            +
                  expect(report.logs).to include(an_object_having_attributes(level: :notice, message: /Applied catalog in .* seconds/))
         | 
| 199 145 | 
             
                end
         | 
| 200 146 |  | 
| 201 147 | 
             
                it "should create report with passed transaction_uuid and job_id" do
         | 
| 202 | 
            -
                   | 
| 203 | 
            -
                  allow(@agent).to receive(:init_storage)
         | 
| 148 | 
            +
                  configurer = Puppet::Configurer.new("test_tuuid", "test_jid")
         | 
| 204 149 |  | 
| 205 150 | 
             
                  report = Puppet::Transaction::Report.new(nil, "test", "aaaa")
         | 
| 206 | 
            -
                  expect(Puppet::Transaction::Report).to receive(:new).with(anything, anything, 'test_tuuid', 'test_jid').and_return(report)
         | 
| 207 | 
            -
                  expect( | 
| 151 | 
            +
                  expect(Puppet::Transaction::Report).to receive(:new).with(anything, anything, 'test_tuuid', 'test_jid', anything).and_return(report)
         | 
| 152 | 
            +
                  expect(configurer).to receive(:send_report).with(report)
         | 
| 208 153 |  | 
| 209 | 
            -
                   | 
| 154 | 
            +
                  configurer.run
         | 
| 210 155 | 
             
                end
         | 
| 211 156 |  | 
| 212 157 | 
             
                it "should send the report" do
         | 
| 213 158 | 
             
                  report = Puppet::Transaction::Report.new(nil, "test", "aaaa")
         | 
| 214 159 | 
             
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 215 | 
            -
                  expect( | 
| 160 | 
            +
                  expect(configurer).to receive(:send_report).with(report)
         | 
| 216 161 |  | 
| 217 162 | 
             
                  expect(report.environment).to eq("test")
         | 
| 218 163 | 
             
                  expect(report.transaction_uuid).to eq("aaaa")
         | 
| 219 164 |  | 
| 220 | 
            -
                   | 
| 165 | 
            +
                  configurer.run
         | 
| 221 166 | 
             
                end
         | 
| 222 167 |  | 
| 223 168 | 
             
                it "should send the transaction report even if the catalog could not be retrieved" do
         | 
| 224 | 
            -
                  expect( | 
| 169 | 
            +
                  expect(configurer).to receive(:retrieve_catalog).and_return(nil)
         | 
| 225 170 |  | 
| 226 171 | 
             
                  report = Puppet::Transaction::Report.new(nil, "test", "aaaa")
         | 
| 227 172 | 
             
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 228 | 
            -
                  expect( | 
| 173 | 
            +
                  expect(configurer).to receive(:send_report).with(report)
         | 
| 229 174 |  | 
| 230 175 | 
             
                  expect(report.environment).to eq("test")
         | 
| 231 176 | 
             
                  expect(report.transaction_uuid).to eq("aaaa")
         | 
| 232 177 |  | 
| 233 | 
            -
                   | 
| 178 | 
            +
                  configurer.run
         | 
| 234 179 | 
             
                end
         | 
| 235 180 |  | 
| 236 181 | 
             
                it "should send the transaction report even if there is a failure" do
         | 
| 237 | 
            -
                  expect( | 
| 182 | 
            +
                  expect(configurer).to receive(:retrieve_catalog).and_raise("whatever")
         | 
| 238 183 |  | 
| 239 184 | 
             
                  report = Puppet::Transaction::Report.new(nil, "test", "aaaa")
         | 
| 240 185 | 
             
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 241 | 
            -
                  expect( | 
| 186 | 
            +
                  expect(configurer).to receive(:send_report).with(report)
         | 
| 242 187 |  | 
| 243 188 | 
             
                  expect(report.environment).to eq("test")
         | 
| 244 189 | 
             
                  expect(report.transaction_uuid).to eq("aaaa")
         | 
| 245 190 |  | 
| 246 | 
            -
                  expect( | 
| 191 | 
            +
                  expect(configurer.run).to be_nil
         | 
| 247 192 | 
             
                end
         | 
| 248 193 |  | 
| 249 194 | 
             
                it "should remove the report as a log destination when the run is finished" do
         | 
| 250 | 
            -
                  report = Puppet::Transaction::Report.new
         | 
| 251 195 | 
             
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 252 196 |  | 
| 253 | 
            -
                   | 
| 197 | 
            +
                  configurer.run
         | 
| 254 198 |  | 
| 255 199 | 
             
                  expect(Puppet::Util::Log.destinations).not_to include(report)
         | 
| 256 200 | 
             
                end
         | 
| 257 201 |  | 
| 258 202 | 
             
                it "should return the report exit_status as the result of the run" do
         | 
| 259 | 
            -
                  report = Puppet::Transaction::Report.new
         | 
| 260 203 | 
             
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 261 204 | 
             
                  expect(report).to receive(:exit_status).and_return(1234)
         | 
| 262 205 |  | 
| 263 | 
            -
                  expect( | 
| 206 | 
            +
                  expect(configurer.run).to eq(1234)
         | 
| 264 207 | 
             
                end
         | 
| 265 208 |  | 
| 266 209 | 
             
                it "should return nil if catalog application fails" do
         | 
| 267 | 
            -
                   | 
| 268 | 
            -
                  report  | 
| 269 | 
            -
                  expect(@agent.run(catalog: @catalog, report: report)).to be_nil
         | 
| 210 | 
            +
                  expect_any_instance_of(Puppet::Resource::Catalog).to receive(:apply).and_raise(Puppet::Error, 'One or more resource dependency cycles detected in graph')
         | 
| 211 | 
            +
                  expect(configurer.run(catalog: catalog, report: report)).to be_nil
         | 
| 270 212 | 
             
                end
         | 
| 271 213 |  | 
| 272 214 | 
             
                it "should send the transaction report even if the pre-run command fails" do
         | 
| 273 | 
            -
                  report = Puppet::Transaction::Report.new
         | 
| 274 215 | 
             
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 275 216 |  | 
| 276 217 | 
             
                  Puppet.settings[:prerun_command] = "/my/command"
         | 
| 277 218 | 
             
                  expect(Puppet::Util::Execution).to receive(:execute).with(["/my/command"]).and_raise(Puppet::ExecutionFailure, "Failed")
         | 
| 278 | 
            -
                  expect( | 
| 219 | 
            +
                  expect(configurer).to receive(:send_report).with(report)
         | 
| 279 220 |  | 
| 280 | 
            -
                  expect( | 
| 221 | 
            +
                  expect(configurer.run).to be_nil
         | 
| 281 222 | 
             
                end
         | 
| 282 223 |  | 
| 283 224 | 
             
                it "should include the pre-run command failure in the report" do
         | 
| 284 | 
            -
                  report = Puppet::Transaction::Report.new
         | 
| 285 225 | 
             
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 286 226 |  | 
| 287 227 | 
             
                  Puppet.settings[:prerun_command] = "/my/command"
         | 
| 288 228 | 
             
                  expect(Puppet::Util::Execution).to receive(:execute).with(["/my/command"]).and_raise(Puppet::ExecutionFailure, "Failed")
         | 
| 289 229 |  | 
| 290 | 
            -
                  expect( | 
| 230 | 
            +
                  expect(configurer.run).to be_nil
         | 
| 291 231 | 
             
                  expect(report.logs.find { |x| x.message =~ /Could not run command from prerun_command/ }).to be
         | 
| 292 232 | 
             
                end
         | 
| 293 233 |  | 
| 294 234 | 
             
                it "should send the transaction report even if the post-run command fails" do
         | 
| 295 | 
            -
                  report = Puppet::Transaction::Report.new
         | 
| 296 235 | 
             
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 297 236 |  | 
| 298 237 | 
             
                  Puppet.settings[:postrun_command] = "/my/command"
         | 
| 299 238 | 
             
                  expect(Puppet::Util::Execution).to receive(:execute).with(["/my/command"]).and_raise(Puppet::ExecutionFailure, "Failed")
         | 
| 300 | 
            -
                  expect( | 
| 239 | 
            +
                  expect(configurer).to receive(:send_report).with(report)
         | 
| 301 240 |  | 
| 302 | 
            -
                  expect( | 
| 241 | 
            +
                  expect(configurer.run).to be_nil
         | 
| 303 242 | 
             
                end
         | 
| 304 243 |  | 
| 305 244 | 
             
                it "should include the post-run command failure in the report" do
         | 
| 306 | 
            -
                  report = Puppet::Transaction::Report.new
         | 
| 307 245 | 
             
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 308 246 |  | 
| 309 247 | 
             
                  Puppet.settings[:postrun_command] = "/my/command"
         | 
| @@ -311,7 +249,7 @@ describe Puppet::Configurer do | |
| 311 249 |  | 
| 312 250 | 
             
                  expect(report).to receive(:<<) { |log, _| expect(log.message).to match(/Could not run command from postrun_command/) }.at_least(:once)
         | 
| 313 251 |  | 
| 314 | 
            -
                  expect( | 
| 252 | 
            +
                  expect(configurer.run).to be_nil
         | 
| 315 253 | 
             
                end
         | 
| 316 254 |  | 
| 317 255 | 
             
                it "should execute post-run command even if the pre-run command fails" do
         | 
| @@ -320,47 +258,42 @@ describe Puppet::Configurer do | |
| 320 258 | 
             
                  expect(Puppet::Util::Execution).to receive(:execute).with(["/my/precommand"]).and_raise(Puppet::ExecutionFailure, "Failed")
         | 
| 321 259 | 
             
                  expect(Puppet::Util::Execution).to receive(:execute).with(["/my/postcommand"])
         | 
| 322 260 |  | 
| 323 | 
            -
                  expect( | 
| 261 | 
            +
                  expect(configurer.run).to be_nil
         | 
| 324 262 | 
             
                end
         | 
| 325 263 |  | 
| 326 264 | 
             
                it "should finalize the report" do
         | 
| 327 | 
            -
                  report = Puppet::Transaction::Report.new
         | 
| 328 265 | 
             
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 329 266 |  | 
| 330 267 | 
             
                  expect(report).to receive(:finalize_report)
         | 
| 331 | 
            -
                   | 
| 268 | 
            +
                  configurer.run
         | 
| 332 269 | 
             
                end
         | 
| 333 270 |  | 
| 334 271 | 
             
                it "should not apply the catalog if the pre-run command fails" do
         | 
| 335 | 
            -
                  report = Puppet::Transaction::Report.new
         | 
| 336 272 | 
             
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 337 273 |  | 
| 338 274 | 
             
                  Puppet.settings[:prerun_command] = "/my/command"
         | 
| 339 275 | 
             
                  expect(Puppet::Util::Execution).to receive(:execute).with(["/my/command"]).and_raise(Puppet::ExecutionFailure, "Failed")
         | 
| 340 276 |  | 
| 341 | 
            -
                   | 
| 342 | 
            -
                  expect( | 
| 277 | 
            +
                  expect_any_instance_of(Puppet::Resource::Catalog).not_to receive(:apply)
         | 
| 278 | 
            +
                  expect(configurer).to receive(:send_report)
         | 
| 343 279 |  | 
| 344 | 
            -
                  expect( | 
| 280 | 
            +
                  expect(configurer.run).to be_nil
         | 
| 345 281 | 
             
                end
         | 
| 346 282 |  | 
| 347 283 | 
             
                it "should apply the catalog, send the report, and return nil if the post-run command fails" do
         | 
| 348 | 
            -
                  report = Puppet::Transaction::Report.new
         | 
| 349 284 | 
             
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 350 285 |  | 
| 351 286 | 
             
                  Puppet.settings[:postrun_command] = "/my/command"
         | 
| 352 287 | 
             
                  expect(Puppet::Util::Execution).to receive(:execute).with(["/my/command"]).and_raise(Puppet::ExecutionFailure, "Failed")
         | 
| 353 288 |  | 
| 354 | 
            -
                   | 
| 355 | 
            -
                  expect( | 
| 289 | 
            +
                  expect_any_instance_of(Puppet::Resource::Catalog).to receive(:apply)
         | 
| 290 | 
            +
                  expect(configurer).to receive(:send_report)
         | 
| 356 291 |  | 
| 357 | 
            -
                  expect( | 
| 292 | 
            +
                  expect(configurer.run).to be_nil
         | 
| 358 293 | 
             
                end
         | 
| 359 294 |  | 
| 360 295 | 
             
                it 'includes total time metrics in the report after successfully applying the catalog' do
         | 
| 361 | 
            -
                  report  | 
| 362 | 
            -
                  allow(@catalog).to receive(:apply).with(hash_including(report: report))
         | 
| 363 | 
            -
                  @agent.run(report: report)
         | 
| 296 | 
            +
                  configurer.run(report: report)
         | 
| 364 297 |  | 
| 365 298 | 
             
                  expect(report.metrics['time']).to be
         | 
| 366 299 | 
             
                  expect(report.metrics['time']['total']).to be_a_kind_of(Numeric)
         | 
| @@ -370,120 +303,109 @@ describe Puppet::Configurer do | |
| 370 303 | 
             
                  Puppet.settings[:prerun_command] = "/my/command"
         | 
| 371 304 | 
             
                  expect(Puppet::Util::Execution).to receive(:execute).with(["/my/command"]).and_raise(Puppet::ExecutionFailure, "Failed")
         | 
| 372 305 |  | 
| 373 | 
            -
                  report  | 
| 374 | 
            -
                  @agent.run(report: report)
         | 
| 306 | 
            +
                  configurer.run(report: report)
         | 
| 375 307 |  | 
| 376 308 | 
             
                  expect(report.metrics['time']).to be
         | 
| 377 309 | 
             
                  expect(report.metrics['time']['total']).to be_a_kind_of(Numeric)
         | 
| 378 310 | 
             
                end
         | 
| 379 311 |  | 
| 380 312 | 
             
                it 'includes total time metrics in the report even if catalog retrieval fails' do
         | 
| 381 | 
            -
                   | 
| 382 | 
            -
                   | 
| 383 | 
            -
                  @agent.run(:report => report)
         | 
| 313 | 
            +
                  allow(configurer).to receive(:prepare_and_retrieve_catalog_from_cache).and_raise
         | 
| 314 | 
            +
                  configurer.run(:report => report)
         | 
| 384 315 |  | 
| 385 316 | 
             
                  expect(report.metrics['time']).to be
         | 
| 386 317 | 
             
                  expect(report.metrics['time']['total']).to be_a_kind_of(Numeric)
         | 
| 387 318 | 
             
                end
         | 
| 388 319 |  | 
| 389 320 | 
             
                it "should refetch the catalog if the server specifies a new environment in the catalog" do
         | 
| 390 | 
            -
                  catalog = Puppet::Resource::Catalog.new( | 
| 391 | 
            -
                  expect( | 
| 321 | 
            +
                  catalog = Puppet::Resource::Catalog.new(node_name, Puppet::Node::Environment.remote('second_env'))
         | 
| 322 | 
            +
                  expect(configurer).to receive(:retrieve_catalog).and_return(catalog).twice
         | 
| 392 323 |  | 
| 393 | 
            -
                   | 
| 324 | 
            +
                  configurer.run
         | 
| 394 325 | 
             
                end
         | 
| 395 326 |  | 
| 396 | 
            -
                it " | 
| 397 | 
            -
                   | 
| 327 | 
            +
                it "changes the configurer's environment if the server specifies a new environment in the catalog" do
         | 
| 328 | 
            +
                  allow_any_instance_of(Puppet::Resource::Catalog).to receive(:environment).and_return("second_env")
         | 
| 398 329 |  | 
| 399 | 
            -
                   | 
| 330 | 
            +
                  configurer.run
         | 
| 400 331 |  | 
| 401 | 
            -
                  expect( | 
| 332 | 
            +
                  expect(configurer.environment).to eq("second_env")
         | 
| 402 333 | 
             
                end
         | 
| 403 334 |  | 
| 404 | 
            -
                it " | 
| 405 | 
            -
                   | 
| 406 | 
            -
                  expect(Puppet::Transaction::Report).to receive(:new).and_return(report)
         | 
| 407 | 
            -
                  expect(@agent).to receive(:send_report).with(report)
         | 
| 408 | 
            -
             | 
| 409 | 
            -
                  allow(@catalog).to receive(:environment).and_return("second_env")
         | 
| 410 | 
            -
                  allow(@agent).to receive(:retrieve_catalog).and_return(@catalog)
         | 
| 335 | 
            +
                it "changes the report's environment if the server specifies a new environment in the catalog" do
         | 
| 336 | 
            +
                  allow_any_instance_of(Puppet::Resource::Catalog).to receive(:environment).and_return("second_env")
         | 
| 411 337 |  | 
| 412 | 
            -
                   | 
| 338 | 
            +
                  configurer.run(report: report)
         | 
| 413 339 |  | 
| 414 340 | 
             
                  expect(report.environment).to eq("second_env")
         | 
| 415 341 | 
             
                end
         | 
| 416 342 |  | 
| 417 343 | 
             
                it "sends the transaction uuid in a catalog request" do
         | 
| 418 | 
            -
                   | 
| 344 | 
            +
                  configurer = Puppet::Configurer.new('aaa')
         | 
| 419 345 | 
             
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(transaction_uuid: 'aaa'))
         | 
| 420 | 
            -
                   | 
| 346 | 
            +
                  configurer.run
         | 
| 421 347 | 
             
                end
         | 
| 422 348 |  | 
| 423 349 | 
             
                it "sends the transaction uuid in a catalog request" do
         | 
| 424 | 
            -
                   | 
| 350 | 
            +
                  configurer = Puppet::Configurer.new('b', 'aaa')
         | 
| 425 351 | 
             
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(job_id: 'aaa'))
         | 
| 426 | 
            -
                   | 
| 352 | 
            +
                  configurer.run
         | 
| 427 353 | 
             
                end
         | 
| 428 354 |  | 
| 429 355 | 
             
                it "sets the static_catalog query param to true in a catalog request" do
         | 
| 430 356 | 
             
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(static_catalog: true))
         | 
| 431 | 
            -
                   | 
| 357 | 
            +
                  configurer.run
         | 
| 432 358 | 
             
                end
         | 
| 433 359 |  | 
| 434 360 | 
             
                it "sets the checksum_type query param to the default supported_checksum_types in a catalog request" do
         | 
| 435 361 | 
             
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything,
         | 
| 436 362 | 
             
                    hash_including(checksum_type: 'md5.sha256.sha384.sha512.sha224'))
         | 
| 437 | 
            -
                   | 
| 363 | 
            +
                  configurer.run
         | 
| 438 364 | 
             
                end
         | 
| 439 365 |  | 
| 440 366 | 
             
                it "sets the checksum_type query param to the supported_checksum_types setting in a catalog request" do
         | 
| 441 | 
            -
                  # Regenerate the agent to pick up the new setting
         | 
| 442 367 | 
             
                  Puppet[:supported_checksum_types] = ['sha256']
         | 
| 443 | 
            -
                   | 
| 444 | 
            -
                   | 
| 445 | 
            -
                  allow(@agent).to receive(:download_plugins)
         | 
| 446 | 
            -
                  allow(@agent).to receive(:send_report)
         | 
| 447 | 
            -
                  allow(@agent).to receive(:save_last_run_summary)
         | 
| 368 | 
            +
                  # Regenerate the agent to pick up the new setting
         | 
| 369 | 
            +
                  configurer = Puppet::Configurer.new
         | 
| 448 370 |  | 
| 449 371 | 
             
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(checksum_type: 'sha256'))
         | 
| 450 | 
            -
                   | 
| 372 | 
            +
                  configurer.run
         | 
| 451 373 | 
             
                end
         | 
| 452 374 |  | 
| 453 375 | 
             
                describe "when not using a REST terminus for catalogs" do
         | 
| 454 376 | 
             
                  it "should not pass any facts when retrieving the catalog" do
         | 
| 377 | 
            +
                    # This is weird, we collect facts when constructing the node,
         | 
| 378 | 
            +
                    # but we don't send them in the indirector request. Then the compiler
         | 
| 379 | 
            +
                    # looks up the node, and collects its facts, which we could have sent
         | 
| 380 | 
            +
                    # in the first place. This seems like a bug.
         | 
| 455 381 | 
             
                    Puppet::Resource::Catalog.indirection.terminus_class = :compiler
         | 
| 456 | 
            -
             | 
| 382 | 
            +
             | 
| 457 383 | 
             
                    expect(Puppet::Resource::Catalog.indirection).to receive(:find) do |name, options|
         | 
| 458 | 
            -
                      options[:facts]. | 
| 459 | 
            -
                    end.and_return( | 
| 384 | 
            +
                      expect(options[:facts]).to be_nil
         | 
| 385 | 
            +
                    end.and_return(catalog)
         | 
| 460 386 |  | 
| 461 | 
            -
                     | 
| 387 | 
            +
                    configurer.run
         | 
| 462 388 | 
             
                  end
         | 
| 463 389 | 
             
                end
         | 
| 464 390 |  | 
| 465 391 | 
             
                describe "when using a REST terminus for catalogs" do
         | 
| 466 | 
            -
                  it "should pass the  | 
| 392 | 
            +
                  it "should pass the url encoded facts and facts format as arguments when retrieving the catalog" do
         | 
| 467 393 | 
             
                    Puppet::Resource::Catalog.indirection.terminus_class = :rest
         | 
| 468 | 
            -
                    # the "facts_for_uploading" are prepeared by first finding facts, and then encoding them
         | 
| 469 | 
            -
                    # this mocks the "find" with a special value 12345, which is then expected back in the
         | 
| 470 | 
            -
                    # call to "encode" - the encode in turn returns mocked data that is asserted as being
         | 
| 471 | 
            -
                    # presented to the catalog terminus as options.
         | 
| 472 | 
            -
                    #
         | 
| 473 | 
            -
                    expect(@agent).to receive(:find_facts).and_return(12345)
         | 
| 474 | 
            -
                    expect(@agent).to receive(:encode_facts).with(12345).and_return(:facts => "myfacts", :facts_format => :foo)
         | 
| 475 | 
            -
                    expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(facts: "myfacts", facts_format: :foo)).and_return(@catalog)
         | 
| 476 | 
            -
             | 
| 477 | 
            -
                    @agent.run
         | 
| 478 | 
            -
                  end
         | 
| 479 | 
            -
                end
         | 
| 480 | 
            -
              end
         | 
| 481 394 |  | 
| 482 | 
            -
             | 
| 483 | 
            -
             | 
| 484 | 
            -
             | 
| 485 | 
            -
             | 
| 486 | 
            -
             | 
| 395 | 
            +
                    facts.values = { 'foo' => 'bar' }
         | 
| 396 | 
            +
                    Puppet::Node::Facts.indirection.save(facts)
         | 
| 397 | 
            +
             | 
| 398 | 
            +
                    expect(
         | 
| 399 | 
            +
                      Puppet::Resource::Catalog.indirection
         | 
| 400 | 
            +
                    ).to receive(:find) do |_, options|
         | 
| 401 | 
            +
                      expect(options[:facts_format]).to eq("application/json")
         | 
| 402 | 
            +
             | 
| 403 | 
            +
                      unescaped = JSON.parse(CGI.unescape(options[:facts]))
         | 
| 404 | 
            +
                      expect(unescaped).to include("values" => {"foo" => "bar"})
         | 
| 405 | 
            +
                    end.and_return(catalog)
         | 
| 406 | 
            +
             | 
| 407 | 
            +
                    configurer.run
         | 
| 408 | 
            +
                  end
         | 
| 487 409 | 
             
                end
         | 
| 488 410 | 
             
              end
         | 
| 489 411 |  | 
| @@ -491,56 +413,52 @@ describe Puppet::Configurer do | |
| 491 413 | 
             
                include PuppetSpec::Files
         | 
| 492 414 |  | 
| 493 415 | 
             
                before do
         | 
| 494 | 
            -
                  allow(Puppet.settings).to receive(:use).and_return(true)
         | 
| 495 | 
            -
                  @configurer = Puppet::Configurer.new
         | 
| 496 416 | 
             
                  Puppet[:lastrunfile] = tmpfile('last_run_file')
         | 
| 497 | 
            -
             | 
| 498 | 
            -
                  @report = Puppet::Transaction::Report.new
         | 
| 499 417 | 
             
                  Puppet[:reports] = "none"
         | 
| 500 418 | 
             
                end
         | 
| 501 419 |  | 
| 502 420 | 
             
                it "should print a report summary if configured to do so" do
         | 
| 503 421 | 
             
                  Puppet.settings[:summarize] = true
         | 
| 504 422 |  | 
| 505 | 
            -
                  expect( | 
| 423 | 
            +
                  expect(report).to receive(:summary).and_return("stuff")
         | 
| 506 424 |  | 
| 507 | 
            -
                  expect( | 
| 508 | 
            -
                   | 
| 425 | 
            +
                  expect(configurer).to receive(:puts).with("stuff")
         | 
| 426 | 
            +
                  configurer.send_report(report)
         | 
| 509 427 | 
             
                end
         | 
| 510 428 |  | 
| 511 429 | 
             
                it "should not print a report summary if not configured to do so" do
         | 
| 512 430 | 
             
                  Puppet.settings[:summarize] = false
         | 
| 513 431 |  | 
| 514 | 
            -
                  expect( | 
| 515 | 
            -
                   | 
| 432 | 
            +
                  expect(configurer).not_to receive(:puts)
         | 
| 433 | 
            +
                  configurer.send_report(report)
         | 
| 516 434 | 
             
                end
         | 
| 517 435 |  | 
| 518 436 | 
             
                it "should save the report if reporting is enabled" do
         | 
| 519 437 | 
             
                  Puppet.settings[:report] = true
         | 
| 520 438 |  | 
| 521 | 
            -
                  expect(Puppet::Transaction::Report.indirection).to receive(:save).with( | 
| 522 | 
            -
                   | 
| 439 | 
            +
                  expect(Puppet::Transaction::Report.indirection).to receive(:save).with(report, nil, instance_of(Hash))
         | 
| 440 | 
            +
                  configurer.send_report(report)
         | 
| 523 441 | 
             
                end
         | 
| 524 442 |  | 
| 525 443 | 
             
                it "should not save the report if reporting is disabled" do
         | 
| 526 444 | 
             
                  Puppet.settings[:report] = false
         | 
| 527 445 |  | 
| 528 | 
            -
                  expect(Puppet::Transaction::Report.indirection).not_to receive(:save).with( | 
| 529 | 
            -
                   | 
| 446 | 
            +
                  expect(Puppet::Transaction::Report.indirection).not_to receive(:save).with(report, nil, instance_of(Hash))
         | 
| 447 | 
            +
                  configurer.send_report(report)
         | 
| 530 448 | 
             
                end
         | 
| 531 449 |  | 
| 532 450 | 
             
                it "should save the last run summary if reporting is enabled" do
         | 
| 533 451 | 
             
                  Puppet.settings[:report] = true
         | 
| 534 452 |  | 
| 535 | 
            -
                  expect( | 
| 536 | 
            -
                   | 
| 453 | 
            +
                  expect(configurer).to receive(:save_last_run_summary).with(report)
         | 
| 454 | 
            +
                  configurer.send_report(report)
         | 
| 537 455 | 
             
                end
         | 
| 538 456 |  | 
| 539 457 | 
             
                it "should save the last run summary if reporting is disabled" do
         | 
| 540 458 | 
             
                  Puppet.settings[:report] = false
         | 
| 541 459 |  | 
| 542 | 
            -
                  expect( | 
| 543 | 
            -
                   | 
| 460 | 
            +
                  expect(configurer).to receive(:save_last_run_summary).with(report)
         | 
| 461 | 
            +
                  configurer.send_report(report)
         | 
| 544 462 | 
             
                end
         | 
| 545 463 |  | 
| 546 464 | 
             
                it "should log but not fail if saving the report fails" do
         | 
| @@ -548,8 +466,9 @@ describe Puppet::Configurer do | |
| 548 466 |  | 
| 549 467 | 
             
                  expect(Puppet::Transaction::Report.indirection).to receive(:save).and_raise("whatever")
         | 
| 550 468 |  | 
| 551 | 
            -
                   | 
| 552 | 
            -
             | 
| 469 | 
            +
                  configurer.send_report(report)
         | 
| 470 | 
            +
             | 
| 471 | 
            +
                  expect(@logs).to include(an_object_having_attributes(level: :err, message: 'Could not send report: whatever'))
         | 
| 553 472 | 
             
                end
         | 
| 554 473 | 
             
              end
         | 
| 555 474 |  | 
| @@ -557,22 +476,17 @@ describe Puppet::Configurer do | |
| 557 476 | 
             
                include PuppetSpec::Files
         | 
| 558 477 |  | 
| 559 478 | 
             
                before do
         | 
| 560 | 
            -
                  allow(Puppet.settings).to receive(:use).and_return(true)
         | 
| 561 | 
            -
                  @configurer = Puppet::Configurer.new
         | 
| 562 | 
            -
             | 
| 563 | 
            -
                  @report = double('report', :raw_summary => {})
         | 
| 564 | 
            -
             | 
| 565 479 | 
             
                  Puppet[:lastrunfile] = tmpfile('last_run_file')
         | 
| 566 480 | 
             
                end
         | 
| 567 481 |  | 
| 568 482 | 
             
                it "should write the last run file" do
         | 
| 569 | 
            -
                   | 
| 483 | 
            +
                  configurer.save_last_run_summary(report)
         | 
| 570 484 | 
             
                  expect(Puppet::FileSystem.exist?(Puppet[:lastrunfile])).to be_truthy
         | 
| 571 485 | 
             
                end
         | 
| 572 486 |  | 
| 573 487 | 
             
                it "should write the raw summary as yaml" do
         | 
| 574 | 
            -
                  expect( | 
| 575 | 
            -
                   | 
| 488 | 
            +
                  expect(report).to receive(:raw_summary).and_return("summary")
         | 
| 489 | 
            +
                  configurer.save_last_run_summary(report)
         | 
| 576 490 | 
             
                  expect(File.read(Puppet[:lastrunfile])).to eq(YAML.dump("summary"))
         | 
| 577 491 | 
             
                end
         | 
| 578 492 |  | 
| @@ -587,13 +501,14 @@ describe Puppet::Configurer do | |
| 587 501 |  | 
| 588 502 | 
             
                  expect(Puppet::Util).to receive(:replace_file).and_yield(fh)
         | 
| 589 503 |  | 
| 590 | 
            -
                   | 
| 591 | 
            -
             | 
| 504 | 
            +
                  configurer.save_last_run_summary(report)
         | 
| 505 | 
            +
             | 
| 506 | 
            +
                  expect(@logs).to include(an_object_having_attributes(level: :err, message: 'Could not save last run local report: failed to do print'))
         | 
| 592 507 | 
             
                end
         | 
| 593 508 |  | 
| 594 509 | 
             
                it "should create the last run file with the correct mode" do
         | 
| 595 510 | 
             
                  expect(Puppet.settings.setting(:lastrunfile)).to receive(:mode).and_return('664')
         | 
| 596 | 
            -
                   | 
| 511 | 
            +
                  configurer.save_last_run_summary(report)
         | 
| 597 512 |  | 
| 598 513 | 
             
                  if Puppet::Util::Platform.windows?
         | 
| 599 514 | 
             
                    require 'puppet/util/windows/security'
         | 
| @@ -606,26 +521,28 @@ describe Puppet::Configurer do | |
| 606 521 |  | 
| 607 522 | 
             
                it "should report invalid last run file permissions" do
         | 
| 608 523 | 
             
                  expect(Puppet.settings.setting(:lastrunfile)).to receive(:mode).and_return('892')
         | 
| 609 | 
            -
             | 
| 610 | 
            -
                   | 
| 524 | 
            +
             | 
| 525 | 
            +
                  configurer.save_last_run_summary(report)
         | 
| 526 | 
            +
             | 
| 527 | 
            +
                  expect(@logs).to include(an_object_having_attributes(level: :err, message: /Could not save last run local report.*892 is invalid/))
         | 
| 611 528 | 
             
                end
         | 
| 612 529 | 
             
              end
         | 
| 613 530 |  | 
| 614 531 | 
             
              describe "when requesting a node" do
         | 
| 615 532 | 
             
                it "uses the transaction uuid in the request" do
         | 
| 616 533 | 
             
                  expect(Puppet::Node.indirection).to receive(:find).with(anything, hash_including(transaction_uuid: anything)).twice
         | 
| 617 | 
            -
                   | 
| 534 | 
            +
                  configurer.run
         | 
| 618 535 | 
             
                end
         | 
| 619 536 |  | 
| 620 537 | 
             
                it "sends an explicitly configured environment request" do
         | 
| 621 538 | 
             
                  expect(Puppet.settings).to receive(:set_by_config?).with(:environment).and_return(true)
         | 
| 622 539 | 
             
                  expect(Puppet::Node.indirection).to receive(:find).with(anything, hash_including(configured_environment: Puppet[:environment])).twice
         | 
| 623 | 
            -
                   | 
| 540 | 
            +
                  configurer.run
         | 
| 624 541 | 
             
                end
         | 
| 625 542 |  | 
| 626 543 | 
             
                it "does not send a configured_environment when using the default" do
         | 
| 627 544 | 
             
                  expect(Puppet::Node.indirection).to receive(:find).with(anything, hash_including(configured_environment: nil)).twice
         | 
| 628 | 
            -
                   | 
| 545 | 
            +
                  configurer.run
         | 
| 629 546 | 
             
                end
         | 
| 630 547 | 
             
              end
         | 
| 631 548 |  | 
| @@ -656,14 +573,6 @@ describe Puppet::Configurer do | |
| 656 573 |  | 
| 657 574 | 
             
              describe "when retrieving a catalog" do
         | 
| 658 575 | 
             
                before do
         | 
| 659 | 
            -
                  allow(Puppet.settings).to receive(:use).and_return(true)
         | 
| 660 | 
            -
                  allow(@agent).to receive(:facts_for_uploading).and_return({})
         | 
| 661 | 
            -
                  allow(@agent).to receive(:download_plugins)
         | 
| 662 | 
            -
             | 
| 663 | 
            -
                  # retrieve a catalog in the current environment, so we don't try to converge unexpectedly
         | 
| 664 | 
            -
                  @catalog = Puppet::Resource::Catalog.new("tester", Puppet::Node::Environment.remote(Puppet[:environment].to_sym))
         | 
| 665 | 
            -
             | 
| 666 | 
            -
                  # this is the default when using a Configurer instance
         | 
| 667 576 | 
             
                  allow(Puppet::Resource::Catalog.indirection).to receive(:terminus_class).and_return(:rest)
         | 
| 668 577 | 
             
                end
         | 
| 669 578 |  | 
| @@ -673,101 +582,139 @@ describe Puppet::Configurer do | |
| 673 582 | 
             
                  end
         | 
| 674 583 |  | 
| 675 584 | 
             
                  it "should first look in the cache for a catalog" do
         | 
| 676 | 
            -
                    expects_cached_catalog_only( | 
| 585 | 
            +
                    expects_cached_catalog_only(catalog)
         | 
| 677 586 |  | 
| 678 | 
            -
                     | 
| 587 | 
            +
                    configurer.run
         | 
| 679 588 | 
             
                  end
         | 
| 680 589 |  | 
| 681 590 | 
             
                  it "should not make a node request or pluginsync when a cached catalog is successfully retrieved" do
         | 
| 682 591 | 
             
                    expect(Puppet::Node.indirection).not_to receive(:find)
         | 
| 683 | 
            -
                    expects_cached_catalog_only( | 
| 684 | 
            -
                    expect( | 
| 592 | 
            +
                    expects_cached_catalog_only(catalog)
         | 
| 593 | 
            +
                    expect(configurer).not_to receive(:download_plugins)
         | 
| 685 594 |  | 
| 686 | 
            -
                     | 
| 595 | 
            +
                    configurer.run
         | 
| 687 596 | 
             
                  end
         | 
| 688 597 |  | 
| 689 598 | 
             
                  it "should make a node request and pluginsync when a cached catalog cannot be retrieved" do
         | 
| 690 599 | 
             
                    expect(Puppet::Node.indirection).to receive(:find).and_return(nil)
         | 
| 691 | 
            -
                    expects_fallback_to_new_catalog( | 
| 692 | 
            -
                    expect( | 
| 600 | 
            +
                    expects_fallback_to_new_catalog(catalog)
         | 
| 601 | 
            +
                    expect(configurer).to receive(:download_plugins)
         | 
| 693 602 |  | 
| 694 | 
            -
                     | 
| 603 | 
            +
                    configurer.run
         | 
| 695 604 | 
             
                  end
         | 
| 696 605 |  | 
| 697 606 | 
             
                  it "should set its cached_catalog_status to 'explicitly_requested'" do
         | 
| 698 | 
            -
                    expects_cached_catalog_only( | 
| 607 | 
            +
                    expects_cached_catalog_only(catalog)
         | 
| 608 | 
            +
             | 
| 609 | 
            +
                    options = {}
         | 
| 610 | 
            +
                    configurer.run(options)
         | 
| 699 611 |  | 
| 700 | 
            -
                     | 
| 701 | 
            -
                    expect(@agent.instance_variable_get(:@cached_catalog_status)).to eq('explicitly_requested')
         | 
| 612 | 
            +
                    expect(options[:report].cached_catalog_status).to eq('explicitly_requested')
         | 
| 702 613 | 
             
                  end
         | 
| 703 614 |  | 
| 704 615 | 
             
                  it "should set its cached_catalog_status to 'explicitly requested' if the cached catalog is from a different environment" do
         | 
| 705 | 
            -
                    cached_catalog = Puppet::Resource::Catalog.new( | 
| 616 | 
            +
                    cached_catalog = Puppet::Resource::Catalog.new(node_name, Puppet::Node::Environment.remote('second_env'))
         | 
| 706 617 | 
             
                    expects_cached_catalog_only(cached_catalog)
         | 
| 707 618 |  | 
| 708 | 
            -
                     | 
| 709 | 
            -
                     | 
| 710 | 
            -
                  end
         | 
| 711 | 
            -
             | 
| 712 | 
            -
                  it "should compile a new catalog if none is found in the cache" do
         | 
| 713 | 
            -
                    expects_fallback_to_new_catalog(@catalog)
         | 
| 619 | 
            +
                    options = {}
         | 
| 620 | 
            +
                    configurer.run(options)
         | 
| 714 621 |  | 
| 715 | 
            -
                    expect( | 
| 622 | 
            +
                    expect(options[:report].cached_catalog_status).to eq('explicitly_requested')
         | 
| 716 623 | 
             
                  end
         | 
| 717 624 |  | 
| 718 | 
            -
                  it "should  | 
| 719 | 
            -
                    expects_fallback_to_new_catalog( | 
| 625 | 
            +
                  it "should pluginsync and compile a new catalog if none is found in the cache" do
         | 
| 626 | 
            +
                    expects_fallback_to_new_catalog(catalog)
         | 
| 627 | 
            +
                    stub_request(:get, %r{/puppet/v3/file_metadatas?/plugins}).to_return(:status => 404)
         | 
| 628 | 
            +
                    stub_request(:get, %r{/puppet/v3/file_metadatas?/pluginfacts}).to_return(:status => 404)
         | 
| 720 629 |  | 
| 721 | 
            -
                     | 
| 722 | 
            -
                     | 
| 630 | 
            +
                    options = {}
         | 
| 631 | 
            +
                    configurer.run(options)
         | 
| 632 | 
            +
             | 
| 633 | 
            +
                    expect(options[:report].cached_catalog_status).to eq('not_used')
         | 
| 723 634 | 
             
                  end
         | 
| 724 635 |  | 
| 725 636 | 
             
                  it "should not attempt to retrieve a cached catalog again if the first attempt failed" do
         | 
| 726 637 | 
             
                    expect(Puppet::Node.indirection).to receive(:find).and_return(nil)
         | 
| 727 638 | 
             
                    expects_neither_new_or_cached_catalog
         | 
| 728 639 |  | 
| 729 | 
            -
                     | 
| 640 | 
            +
                    # after failing to use a cached catalog, we'll need to pluginsync before getting
         | 
| 641 | 
            +
                    # a new catalog, which also fails.
         | 
| 642 | 
            +
                    stub_request(:get, %r{/puppet/v3/file_metadatas?/plugins}).to_return(:status => 404)
         | 
| 643 | 
            +
                    stub_request(:get, %r{/puppet/v3/file_metadatas?/pluginfacts}).to_return(:status => 404)
         | 
| 644 | 
            +
             | 
| 645 | 
            +
                    configurer.run
         | 
| 730 646 | 
             
                  end
         | 
| 731 647 |  | 
| 732 648 | 
             
                  it "should return the cached catalog when the environment doesn't match" do
         | 
| 733 | 
            -
                    cached_catalog = Puppet::Resource::Catalog.new( | 
| 649 | 
            +
                    cached_catalog = Puppet::Resource::Catalog.new(node_name, Puppet::Node::Environment.remote('second_env'))
         | 
| 734 650 | 
             
                    expects_cached_catalog_only(cached_catalog)
         | 
| 735 651 |  | 
| 652 | 
            +
                    allow(Puppet).to receive(:info)
         | 
| 736 653 | 
             
                    expect(Puppet).to receive(:info).with("Using cached catalog from environment 'second_env'")
         | 
| 737 | 
            -
             | 
| 654 | 
            +
             | 
| 655 | 
            +
                    configurer.run
         | 
| 656 | 
            +
                  end
         | 
| 657 | 
            +
             | 
| 658 | 
            +
                  it "applies the catalog passed as options when the catalog cache terminus is not set" do
         | 
| 659 | 
            +
                    stub_request(:get, %r{/puppet/v3/file_metadatas?/plugins}).to_return(:status => 404)
         | 
| 660 | 
            +
                    stub_request(:get, %r{/puppet/v3/file_metadatas?/pluginfacts}).to_return(:status => 404)
         | 
| 661 | 
            +
             | 
| 662 | 
            +
                    catalog.add_resource(Puppet::Resource.new('notify', 'from apply'))
         | 
| 663 | 
            +
                    configurer.run(catalog: catalog.to_ral)
         | 
| 664 | 
            +
             | 
| 665 | 
            +
                    # make sure cache class is not set to avoid surprises later
         | 
| 666 | 
            +
                    expect(Puppet::Resource::Catalog.indirection).to_not be_cache
         | 
| 667 | 
            +
                    expect(@logs).to include(an_object_having_attributes(level: :notice, message: /defined 'message' as 'from apply'/))
         | 
| 668 | 
            +
                  end
         | 
| 669 | 
            +
             | 
| 670 | 
            +
                  it "applies the cached catalog when the catalog cache terminus is set, ignoring the catalog passed as options" do
         | 
| 671 | 
            +
                    Puppet::Resource::Catalog.indirection.cache_class = :json
         | 
| 672 | 
            +
             | 
| 673 | 
            +
                    cached_catalog = Puppet::Resource::Catalog.new(Puppet[:node_name_value], Puppet[:environment])
         | 
| 674 | 
            +
                    cached_catalog.add_resource(Puppet::Resource.new('notify', 'from cache'))
         | 
| 675 | 
            +
             | 
| 676 | 
            +
                    # update cached catalog
         | 
| 677 | 
            +
                    Puppet.settings.use(:main, :agent)
         | 
| 678 | 
            +
                    path = Puppet::Resource::Catalog.indirection.cache.path(cached_catalog.name)
         | 
| 679 | 
            +
                    FileUtils.mkdir(File.dirname(path))
         | 
| 680 | 
            +
                    File.write(path, cached_catalog.render(:json))
         | 
| 681 | 
            +
             | 
| 682 | 
            +
                    configurer.run(catalog: catalog.to_ral)
         | 
| 683 | 
            +
             | 
| 684 | 
            +
                    expect(@logs).to include(an_object_having_attributes(level: :notice, message: /defined 'message' as 'from cache'/))
         | 
| 738 685 | 
             
                  end
         | 
| 739 686 | 
             
                end
         | 
| 740 687 |  | 
| 741 688 | 
             
                describe "and strict environment mode is set" do
         | 
| 742 689 | 
             
                  before do
         | 
| 743 | 
            -
                    allow(@catalog).to receive(:to_ral).and_return(@catalog)
         | 
| 744 | 
            -
                    allow(@catalog).to receive(:write_class_file)
         | 
| 745 | 
            -
                    allow(@catalog).to receive(:write_resource_file)
         | 
| 746 | 
            -
                    allow(@agent).to receive(:send_report)
         | 
| 747 | 
            -
                    allow(@agent).to receive(:save_last_run_summary)
         | 
| 748 690 | 
             
                    Puppet.settings[:strict_environment_mode] = true
         | 
| 749 691 | 
             
                  end
         | 
| 750 692 |  | 
| 751 693 | 
             
                  it "should not make a node request" do
         | 
| 752 | 
            -
                     | 
| 694 | 
            +
                    stub_request(:get, %r{/puppet/v3/file_metadatas?/plugins}).to_return(:status => 404)
         | 
| 695 | 
            +
                    stub_request(:get, %r{/puppet/v3/file_metadatas?/pluginfacts}).to_return(:status => 404)
         | 
| 696 | 
            +
                    expects_new_catalog_only(catalog)
         | 
| 697 | 
            +
             | 
| 753 698 | 
             
                    expect(Puppet::Node.indirection).not_to receive(:find)
         | 
| 754 699 |  | 
| 755 | 
            -
                     | 
| 700 | 
            +
                    configurer.run
         | 
| 756 701 | 
             
                  end
         | 
| 757 702 |  | 
| 758 703 | 
             
                  it "should return nil when the catalog's environment doesn't match the agent specified environment" do
         | 
| 759 | 
            -
                     | 
| 760 | 
            -
                     | 
| 704 | 
            +
                    Puppet[:environment] = 'second_env'
         | 
| 705 | 
            +
                    configurer = Puppet::Configurer.new
         | 
| 706 | 
            +
             | 
| 707 | 
            +
                    catalog = Puppet::Resource::Catalog.new(node_name, Puppet::Node::Environment.remote("production"))
         | 
| 708 | 
            +
                    expects_new_catalog_only(catalog)
         | 
| 761 709 |  | 
| 762 710 | 
             
                    expect(Puppet).to receive(:err).with("Not using catalog because its environment 'production' does not match agent specified environment 'second_env' and strict_environment_mode is set")
         | 
| 763 | 
            -
                    expect( | 
| 711 | 
            +
                    expect(configurer.run).to be_nil
         | 
| 764 712 | 
             
                  end
         | 
| 765 713 |  | 
| 766 | 
            -
                  it "should  | 
| 767 | 
            -
                     | 
| 768 | 
            -
                    expects_new_catalog_only(@catalog)
         | 
| 714 | 
            +
                  it "should return 0 when the catalog's environment matches the agent specified environment" do
         | 
| 715 | 
            +
                    expects_new_catalog_only(catalog)
         | 
| 769 716 |  | 
| 770 | 
            -
                    expect( | 
| 717 | 
            +
                    expect(configurer.run).to eq(0)
         | 
| 771 718 | 
             
                  end
         | 
| 772 719 |  | 
| 773 720 | 
             
                  describe "and a cached catalog is explicitly requested" do
         | 
| @@ -776,83 +723,81 @@ describe Puppet::Configurer do | |
| 776 723 | 
             
                    end
         | 
| 777 724 |  | 
| 778 725 | 
             
                    it "should return nil when the cached catalog's environment doesn't match the agent specified environment" do
         | 
| 779 | 
            -
                       | 
| 780 | 
            -
                       | 
| 726 | 
            +
                      Puppet[:environment] = 'second_env'
         | 
| 727 | 
            +
                      configurer = Puppet::Configurer.new
         | 
| 728 | 
            +
             | 
| 729 | 
            +
                      catalog = Puppet::Resource::Catalog.new(node_name, Puppet::Node::Environment.remote("production"))
         | 
| 730 | 
            +
                      expects_cached_catalog_only(catalog)
         | 
| 781 731 |  | 
| 782 732 | 
             
                      expect(Puppet).to receive(:err).with("Not using catalog because its environment 'production' does not match agent specified environment 'second_env' and strict_environment_mode is set")
         | 
| 783 | 
            -
                      expect( | 
| 733 | 
            +
                      expect(configurer.run).to be_nil
         | 
| 784 734 | 
             
                    end
         | 
| 785 735 |  | 
| 786 736 | 
             
                    it "should proceed with the cached catalog if its environment matchs the local environment" do
         | 
| 787 | 
            -
                       | 
| 788 | 
            -
                      @agent.instance_variable_set(:@environment, 'production')
         | 
| 789 | 
            -
                      expects_cached_catalog_only(@catalog)
         | 
| 737 | 
            +
                      expects_cached_catalog_only(catalog)
         | 
| 790 738 |  | 
| 791 | 
            -
                      expect( | 
| 739 | 
            +
                      expect(configurer.run).to eq(0)
         | 
| 792 740 | 
             
                    end
         | 
| 793 741 | 
             
                  end
         | 
| 794 742 | 
             
                end
         | 
| 795 743 |  | 
| 796 | 
            -
                it "should use the Catalog class to get its catalog" do
         | 
| 797 | 
            -
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).and_return(@catalog)
         | 
| 798 | 
            -
             | 
| 799 | 
            -
                  @agent.retrieve_catalog({})
         | 
| 800 | 
            -
                end
         | 
| 801 | 
            -
             | 
| 802 744 | 
             
                it "should set its cached_catalog_status to 'not_used' when downloading a new catalog" do
         | 
| 803 | 
            -
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(ignore_cache: true)).and_return( | 
| 745 | 
            +
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(ignore_cache: true)).and_return(catalog)
         | 
| 804 746 |  | 
| 805 | 
            -
                   | 
| 806 | 
            -
                   | 
| 747 | 
            +
                  options = {}
         | 
| 748 | 
            +
                  configurer.run(options)
         | 
| 749 | 
            +
             | 
| 750 | 
            +
                  expect(options[:report].cached_catalog_status).to eq('not_used')
         | 
| 807 751 | 
             
                end
         | 
| 808 752 |  | 
| 809 753 | 
             
                it "should use its node_name_value to retrieve the catalog" do
         | 
| 810 | 
            -
                   | 
| 811 | 
            -
                  Puppet. | 
| 812 | 
            -
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with("myhost.domain.com", anything).and_return(@catalog)
         | 
| 754 | 
            +
                  myhost_facts = Puppet::Node::Facts.new("myhost.domain.com")
         | 
| 755 | 
            +
                  Puppet::Node::Facts.indirection.save(myhost_facts)
         | 
| 813 756 |  | 
| 814 | 
            -
                   | 
| 815 | 
            -
             | 
| 816 | 
            -
             | 
| 817 | 
            -
                it "should default to returning a catalog retrieved directly from the server, skipping the cache" do
         | 
| 818 | 
            -
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(ignore_cache: true)).and_return(@catalog)
         | 
| 757 | 
            +
                  Puppet.settings[:node_name_value] = "myhost.domain.com"
         | 
| 758 | 
            +
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with("myhost.domain.com", anything).and_return(catalog)
         | 
| 819 759 |  | 
| 820 | 
            -
                   | 
| 760 | 
            +
                  configurer.run
         | 
| 821 761 | 
             
                end
         | 
| 822 762 |  | 
| 823 | 
            -
                it "should log  | 
| 824 | 
            -
                  expects_fallback_to_cached_catalog( | 
| 763 | 
            +
                it "should log when no catalog can be retrieved from the server" do
         | 
| 764 | 
            +
                  expects_fallback_to_cached_catalog(catalog)
         | 
| 825 765 |  | 
| 766 | 
            +
                  allow(Puppet).to receive(:info)
         | 
| 826 767 | 
             
                  expect(Puppet).to receive(:info).with("Using cached catalog from environment 'production'")
         | 
| 827 | 
            -
                   | 
| 768 | 
            +
                  configurer.run
         | 
| 828 769 | 
             
                end
         | 
| 829 770 |  | 
| 830 771 | 
             
                it "should set its cached_catalog_status to 'on_failure' when no catalog can be retrieved from the server" do
         | 
| 831 | 
            -
                  expects_fallback_to_cached_catalog( | 
| 772 | 
            +
                  expects_fallback_to_cached_catalog(catalog)
         | 
| 832 773 |  | 
| 833 | 
            -
                   | 
| 834 | 
            -
                   | 
| 774 | 
            +
                  options = {}
         | 
| 775 | 
            +
                  configurer.run(options)
         | 
| 776 | 
            +
             | 
| 777 | 
            +
                  expect(options[:report].cached_catalog_status).to eq('on_failure')
         | 
| 835 778 | 
             
                end
         | 
| 836 779 |  | 
| 837 780 | 
             
                it "should not look in the cache for a catalog if one is returned from the server" do
         | 
| 838 | 
            -
                  expects_new_catalog_only( | 
| 781 | 
            +
                  expects_new_catalog_only(catalog)
         | 
| 839 782 |  | 
| 840 | 
            -
                   | 
| 783 | 
            +
                  configurer.run
         | 
| 841 784 | 
             
                end
         | 
| 842 785 |  | 
| 843 786 | 
             
                it "should return the cached catalog when retrieving the remote catalog throws an exception" do
         | 
| 844 787 | 
             
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(ignore_cache: true)).and_raise("eh")
         | 
| 845 | 
            -
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(ignore_terminus: true)).and_return( | 
| 788 | 
            +
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(ignore_terminus: true)).and_return(catalog)
         | 
| 846 789 |  | 
| 847 | 
            -
                   | 
| 790 | 
            +
                  configurer.run
         | 
| 848 791 | 
             
                end
         | 
| 849 792 |  | 
| 850 793 | 
             
                it "should set its cached_catalog_status to 'on_failure' when retrieving the remote catalog throws an exception" do
         | 
| 851 794 | 
             
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(ignore_cache: true)).and_raise("eh")
         | 
| 852 | 
            -
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(ignore_terminus: true)).and_return( | 
| 795 | 
            +
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(ignore_terminus: true)).and_return(catalog)
         | 
| 796 | 
            +
             | 
| 797 | 
            +
                  options = {}
         | 
| 798 | 
            +
                  configurer.run(options)
         | 
| 853 799 |  | 
| 854 | 
            -
                   | 
| 855 | 
            -
                  expect(@agent.instance_variable_get(:@cached_catalog_status)).to eq('on_failure')
         | 
| 800 | 
            +
                  expect(options[:report].cached_catalog_status).to eq('on_failure')
         | 
| 856 801 | 
             
                end
         | 
| 857 802 |  | 
| 858 803 | 
             
                it "should log and return nil if no catalog can be retrieved from the server and :usecacheonfailure is disabled" do
         | 
| @@ -861,120 +806,173 @@ describe Puppet::Configurer do | |
| 861 806 |  | 
| 862 807 | 
             
                  expect(Puppet).to receive(:warning).with('Not using cache on failed catalog')
         | 
| 863 808 |  | 
| 864 | 
            -
                  expect( | 
| 809 | 
            +
                  expect(configurer.run).to be_nil
         | 
| 865 810 | 
             
                end
         | 
| 866 811 |  | 
| 867 812 | 
             
                it "should set its cached_catalog_status to 'not_used' if no catalog can be retrieved from the server and :usecacheonfailure is disabled or fails to retrieve a catalog" do
         | 
| 868 813 | 
             
                  Puppet[:usecacheonfailure] = false
         | 
| 869 814 | 
             
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(ignore_cache: true)).and_return(nil)
         | 
| 870 815 |  | 
| 871 | 
            -
                   | 
| 872 | 
            -
                   | 
| 816 | 
            +
                  options = {}
         | 
| 817 | 
            +
                  configurer.run(options)
         | 
| 818 | 
            +
             | 
| 819 | 
            +
                  expect(options[:report].cached_catalog_status).to eq('not_used')
         | 
| 873 820 | 
             
                end
         | 
| 874 821 |  | 
| 875 822 | 
             
                it "should return nil if no cached catalog is available and no catalog can be retrieved from the server" do
         | 
| 876 823 | 
             
                  expects_neither_new_or_cached_catalog
         | 
| 877 824 |  | 
| 878 | 
            -
                  expect( | 
| 825 | 
            +
                  expect(configurer.run).to be_nil
         | 
| 879 826 | 
             
                end
         | 
| 880 827 |  | 
| 881 828 | 
             
                it "should return nil if its cached catalog environment doesn't match server-specified environment" do
         | 
| 882 | 
            -
                  cached_catalog = Puppet::Resource::Catalog.new( | 
| 883 | 
            -
                  @agent.instance_variable_set(:@node_environment, 'production')
         | 
| 829 | 
            +
                  cached_catalog = Puppet::Resource::Catalog.new(node_name, Puppet::Node::Environment.remote('second_env'))
         | 
| 884 830 |  | 
| 885 831 | 
             
                  expects_fallback_to_cached_catalog(cached_catalog)
         | 
| 886 832 |  | 
| 833 | 
            +
                  allow(Puppet).to receive(:err)
         | 
| 887 834 | 
             
                  expect(Puppet).to receive(:err).with("Not using cached catalog because its environment 'second_env' does not match 'production'")
         | 
| 888 | 
            -
                  expect( | 
| 835 | 
            +
                  expect(configurer.run).to be_nil
         | 
| 889 836 | 
             
                end
         | 
| 890 837 |  | 
| 891 838 | 
             
                it "should set its cached_catalog_status to 'not_used' if the cached catalog environment doesn't match server-specified environment" do
         | 
| 892 | 
            -
                  cached_catalog = Puppet::Resource::Catalog.new( | 
| 893 | 
            -
                  @agent.instance_variable_set(:@node_environment, 'production')
         | 
| 839 | 
            +
                  cached_catalog = Puppet::Resource::Catalog.new(node_name, Puppet::Node::Environment.remote('second_env'))
         | 
| 894 840 |  | 
| 895 841 | 
             
                  expects_fallback_to_cached_catalog(cached_catalog)
         | 
| 896 842 |  | 
| 897 | 
            -
                   | 
| 898 | 
            -
                   | 
| 899 | 
            -
             | 
| 900 | 
            -
             | 
| 901 | 
            -
                it "should return its cached catalog if the environment matches the server-specified environment" do
         | 
| 902 | 
            -
                  cached_catalog = Puppet::Resource::Catalog.new("tester", Puppet::Node::Environment.remote(Puppet[:environment]))
         | 
| 903 | 
            -
                  @agent.instance_variable_set(:@node_environment, cached_catalog.environment)
         | 
| 904 | 
            -
             | 
| 905 | 
            -
                  expects_fallback_to_cached_catalog(cached_catalog)
         | 
| 906 | 
            -
             | 
| 907 | 
            -
                  expect(@agent.retrieve_catalog({})).to eq(cached_catalog)
         | 
| 843 | 
            +
                  options = {}
         | 
| 844 | 
            +
                  configurer.run(options)
         | 
| 845 | 
            +
                  expect(options[:report].cached_catalog_status).to eq('not_used')
         | 
| 908 846 | 
             
                end
         | 
| 909 847 |  | 
| 910 848 | 
             
                it "should set its cached_catalog_status to 'on_failure' if the cached catalog environment matches server-specified environment" do
         | 
| 911 | 
            -
                   | 
| 912 | 
            -
                  @agent.instance_variable_set(:@node_environment, cached_catalog.environment)
         | 
| 913 | 
            -
             | 
| 914 | 
            -
                  expects_fallback_to_cached_catalog(cached_catalog)
         | 
| 849 | 
            +
                  expects_fallback_to_cached_catalog(catalog)
         | 
| 915 850 |  | 
| 916 | 
            -
                   | 
| 917 | 
            -
                   | 
| 851 | 
            +
                  options = {}
         | 
| 852 | 
            +
                  configurer.run(options)
         | 
| 853 | 
            +
                  expect(options[:report].cached_catalog_status).to eq('on_failure')
         | 
| 918 854 | 
             
                end
         | 
| 919 855 |  | 
| 920 856 | 
             
                it "should not update the cached catalog in noop mode" do
         | 
| 921 857 | 
             
                  Puppet[:noop] = true
         | 
| 922 | 
            -
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).with(anything, hash_including(ignore_cache: true, ignore_cache_save: true)).and_return(@catalog)
         | 
| 923 858 |  | 
| 924 | 
            -
                   | 
| 859 | 
            +
                  stub_request(:post, %r{/puppet/v3/catalog}).to_return(:status => 200, :body => catalog.render(:json), :headers => {'Content-Type' => 'application/json'})
         | 
| 860 | 
            +
             | 
| 861 | 
            +
                  Puppet::Resource::Catalog.indirection.cache_class = :json
         | 
| 862 | 
            +
                  path = Puppet::Resource::Catalog.indirection.cache.path(catalog.name)
         | 
| 863 | 
            +
             | 
| 864 | 
            +
                  expect(File).to_not be_exist(path)
         | 
| 865 | 
            +
                  configurer.run
         | 
| 866 | 
            +
                  expect(File).to_not be_exist(path)
         | 
| 925 867 | 
             
                end
         | 
| 926 868 |  | 
| 927 869 | 
             
                it "should update the cached catalog when not in noop mode" do
         | 
| 928 870 | 
             
                  Puppet[:noop] = false
         | 
| 929 | 
            -
                   | 
| 871 | 
            +
                  Puppet[:log_level] = 'info'
         | 
| 872 | 
            +
             | 
| 873 | 
            +
                  stub_request(:post, %r{/puppet/v3/catalog}).to_return(:status => 200, :body => catalog.render(:json), :headers => {'Content-Type' => 'application/json'})
         | 
| 874 | 
            +
             | 
| 875 | 
            +
                  Puppet::Resource::Catalog.indirection.cache_class = :json
         | 
| 876 | 
            +
                  cache_path = Puppet::Resource::Catalog.indirection.cache.path(Puppet[:node_name_value])
         | 
| 877 | 
            +
             | 
| 878 | 
            +
                  expect(File).to_not be_exist(cache_path)
         | 
| 879 | 
            +
                  configurer.run
         | 
| 880 | 
            +
                  expect(File).to be_exist(cache_path)
         | 
| 881 | 
            +
             | 
| 882 | 
            +
                  expect(@logs).to include(an_object_having_attributes(level: :info, message: "Caching catalog for #{Puppet[:node_name_value]}"))
         | 
| 883 | 
            +
                end
         | 
| 884 | 
            +
             | 
| 885 | 
            +
                it "successfully applies the catalog without a cache" do
         | 
| 886 | 
            +
                  stub_request(:post, %r{/puppet/v3/catalog}).to_return(:status => 200, :body => catalog.render(:json), :headers => {'Content-Type' => 'application/json'})
         | 
| 887 | 
            +
             | 
| 888 | 
            +
                  Puppet::Resource::Catalog.indirection.cache_class = nil
         | 
| 889 | 
            +
             | 
| 890 | 
            +
                  expect(configurer.run).to eq(0)
         | 
| 891 | 
            +
                end
         | 
| 892 | 
            +
             | 
| 893 | 
            +
                it "should not update the cached catalog when running puppet apply" do
         | 
| 894 | 
            +
                  Puppet::Resource::Catalog.indirection.cache_class = :json
         | 
| 895 | 
            +
                  path = Puppet::Resource::Catalog.indirection.cache.path(catalog.name)
         | 
| 930 896 |  | 
| 931 | 
            -
                   | 
| 897 | 
            +
                  expect(File).to_not be_exist(path)
         | 
| 898 | 
            +
                  configurer.run(catalog: catalog)
         | 
| 899 | 
            +
                  expect(File).to_not be_exist(path)
         | 
| 932 900 | 
             
                end
         | 
| 933 901 | 
             
              end
         | 
| 934 902 |  | 
| 935 | 
            -
              describe "when  | 
| 936 | 
            -
                 | 
| 937 | 
            -
             | 
| 903 | 
            +
              describe "when converging the environment" do
         | 
| 904 | 
            +
                let(:apple) { Puppet::Resource::Catalog.new(Puppet[:node_name_value], Puppet::Node::Environment.remote('apple')) }
         | 
| 905 | 
            +
                let(:banana) { Puppet::Resource::Catalog.new(Puppet[:node_name_value], Puppet::Node::Environment.remote('banana')) }
         | 
| 938 906 |  | 
| 939 | 
            -
             | 
| 907 | 
            +
                before :each do
         | 
| 908 | 
            +
                  apple.add_resource(resource)
         | 
| 909 | 
            +
                  banana.add_resource(resource)
         | 
| 940 910 | 
             
                end
         | 
| 941 911 |  | 
| 942 | 
            -
                 | 
| 943 | 
            -
             | 
| 912 | 
            +
                it "converges after multiple attempts" do
         | 
| 913 | 
            +
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).and_return(apple, banana, banana)
         | 
| 914 | 
            +
             | 
| 915 | 
            +
                  allow(Puppet).to receive(:notice)
         | 
| 916 | 
            +
                  expect(Puppet).to receive(:notice).with("Local environment: 'production' doesn't match server specified environment 'apple', restarting agent run with environment 'apple'")
         | 
| 917 | 
            +
                  expect(Puppet).to receive(:notice).with("Local environment: 'apple' doesn't match server specified environment 'banana', restarting agent run with environment 'banana'")
         | 
| 944 918 |  | 
| 945 | 
            -
             | 
| 946 | 
            -
                  expect(@agent.convert_catalog(catalog, 10)).to equal(ral_catalog)
         | 
| 919 | 
            +
                  configurer.run
         | 
| 947 920 | 
             
                end
         | 
| 948 921 |  | 
| 949 | 
            -
                it " | 
| 950 | 
            -
                  expect( | 
| 922 | 
            +
                it "raises if it can't converge after 4 tries after the initial catalog request" do
         | 
| 923 | 
            +
                  expect(Puppet::Resource::Catalog.indirection).to receive(:find).and_return(apple, banana, apple, banana, apple)
         | 
| 951 924 |  | 
| 952 | 
            -
                   | 
| 925 | 
            +
                  configurer.run
         | 
| 926 | 
            +
             | 
| 927 | 
            +
                  expect(@logs).to include(an_object_having_attributes(level: :err, message: "Failed to apply catalog: Catalog environment didn't stabilize after 4 fetches, aborting run"))
         | 
| 953 928 | 
             
                end
         | 
| 929 | 
            +
              end
         | 
| 954 930 |  | 
| 955 | 
            -
             | 
| 956 | 
            -
             | 
| 931 | 
            +
              describe "when converting the catalog" do
         | 
| 932 | 
            +
                it "converts Puppet::Resource into Puppet::Type::Notify" do
         | 
| 933 | 
            +
                  expect(configurer).to receive(:apply_catalog) do |ral, _|
         | 
| 934 | 
            +
                    expect(ral.resources).to contain(an_instance_of(Puppet::Type::Notify))
         | 
| 935 | 
            +
                  end
         | 
| 957 936 |  | 
| 958 | 
            -
                   | 
| 937 | 
            +
                  configurer.run(catalog: catalog)
         | 
| 959 938 | 
             
                end
         | 
| 960 939 |  | 
| 961 | 
            -
                it " | 
| 962 | 
            -
                  expect( | 
| 940 | 
            +
                it "adds default schedules" do
         | 
| 941 | 
            +
                  expect(configurer).to receive(:apply_catalog) do |ral, _|
         | 
| 942 | 
            +
                    expect(ral.resources.map(&:to_ref)).to contain(%w{Schedule[puppet] Schedule[hourly] Schedule[daily] Schedule[weekly] Schedule[monthly] Schedule[never]})
         | 
| 943 | 
            +
                  end
         | 
| 944 | 
            +
             | 
| 945 | 
            +
                  configurer.run
         | 
| 946 | 
            +
                end
         | 
| 947 | 
            +
             | 
| 948 | 
            +
                it "records the retrieval duration to the catalog" do
         | 
| 949 | 
            +
                  expect(configurer).to receive(:apply_catalog) do |ral, _|
         | 
| 950 | 
            +
                    expect(ral.retrieval_duration).to be_an_instance_of(Float)
         | 
| 951 | 
            +
                  end
         | 
| 963 952 |  | 
| 964 | 
            -
                   | 
| 953 | 
            +
                  configurer.run
         | 
| 965 954 | 
             
                end
         | 
| 966 955 |  | 
| 967 | 
            -
                it " | 
| 968 | 
            -
                  expect( | 
| 956 | 
            +
                it "writes the class file containing applied settings classes" do
         | 
| 957 | 
            +
                  expect(File).to_not be_exist(Puppet[:classfile])
         | 
| 958 | 
            +
             | 
| 959 | 
            +
                  configurer.run
         | 
| 969 960 |  | 
| 970 | 
            -
                   | 
| 961 | 
            +
                  expect(File.read(Puppet[:classfile]).chomp).to eq('settings')
         | 
| 971 962 | 
             
                end
         | 
| 972 963 |  | 
| 973 | 
            -
                it " | 
| 974 | 
            -
                   | 
| 964 | 
            +
                it "writes an empty resource file since no resources are 'managed'" do
         | 
| 965 | 
            +
                  expect(File).to_not be_exist(Puppet[:resourcefile])
         | 
| 975 966 |  | 
| 976 | 
            -
                   | 
| 977 | 
            -
             | 
| 967 | 
            +
                  configurer.run
         | 
| 968 | 
            +
             | 
| 969 | 
            +
                  expect(File.read(Puppet[:resourcefile]).chomp).to eq("")
         | 
| 970 | 
            +
                end
         | 
| 971 | 
            +
             | 
| 972 | 
            +
                it "adds the conversion time to the report" do
         | 
| 973 | 
            +
                  configurer.run(report: report)
         | 
| 974 | 
            +
             | 
| 975 | 
            +
                  expect(report.metrics['time']['convert_catalog']).to be_an_instance_of(Float)
         | 
| 978 976 | 
             
                end
         | 
| 979 977 | 
             
              end
         | 
| 980 978 |  | 
| @@ -995,66 +993,62 @@ describe Puppet::Configurer do | |
| 995 993 | 
             
              describe "when attempting failover" do
         | 
| 996 994 | 
             
                it "should not failover if server_list is not set" do
         | 
| 997 995 | 
             
                  Puppet.settings[:server_list] = []
         | 
| 998 | 
            -
                   | 
| 999 | 
            -
                  @agent.run
         | 
| 996 | 
            +
                  configurer.run
         | 
| 1000 997 | 
             
                end
         | 
| 1001 998 |  | 
| 1002 999 | 
             
                it "should not failover during an apply run" do
         | 
| 1003 1000 | 
             
                  Puppet.settings[:server_list] = ["myserver:123"]
         | 
| 1004 | 
            -
                   | 
| 1005 | 
            -
                   | 
| 1006 | 
            -
                  @agent.run :catalog => catalog
         | 
| 1001 | 
            +
                  catalog = Puppet::Resource::Catalog.new(node_name, Puppet::Node::Environment.remote(Puppet[:environment].to_sym))
         | 
| 1002 | 
            +
                  configurer.run(catalog: catalog)
         | 
| 1007 1003 | 
             
                end
         | 
| 1008 1004 |  | 
| 1009 1005 | 
             
                it "should select a server when it receives 200 OK response" do
         | 
| 1010 1006 | 
             
                  Puppet.settings[:server_list] = ["myserver:123"]
         | 
| 1011 | 
            -
             | 
| 1012 | 
            -
                   | 
| 1013 | 
            -
                  allow(@agent).to receive(:run_internal)
         | 
| 1007 | 
            +
             | 
| 1008 | 
            +
                  stub_request(:get, 'https://myserver:123/status/v1/simple/master').to_return(status: 200)
         | 
| 1014 1009 |  | 
| 1015 1010 | 
             
                  options = {}
         | 
| 1016 | 
            -
                   | 
| 1011 | 
            +
                  configurer.run(options)
         | 
| 1017 1012 | 
             
                  expect(options[:report].master_used).to eq('myserver:123')
         | 
| 1018 1013 | 
             
                end
         | 
| 1019 1014 |  | 
| 1020 | 
            -
                it "queries the simple status for the 'master' service" do
         | 
| 1021 | 
            -
                  Puppet.settings[:server_list] = ["myserver:123"]
         | 
| 1022 | 
            -
                  response = Net::HTTPOK.new(nil, 200, 'OK')
         | 
| 1023 | 
            -
                  http = double('request')
         | 
| 1024 | 
            -
                  expect(http).to receive(:get).with('/status/v1/simple/master').and_return(response)
         | 
| 1025 | 
            -
                  allow(Puppet::Network::HttpPool).to receive(:connection).with('myserver', 123, anything).and_return(http)
         | 
| 1026 | 
            -
                  allow(@agent).to receive(:run_internal)
         | 
| 1027 | 
            -
             | 
| 1028 | 
            -
                  @agent.run
         | 
| 1029 | 
            -
                end
         | 
| 1030 | 
            -
             | 
| 1031 1015 | 
             
                it "should report when a server is unavailable" do
         | 
| 1032 1016 | 
             
                  Puppet.settings[:server_list] = ["myserver:123"]
         | 
| 1033 | 
            -
                  response = Net::HTTPInternalServerError.new(nil, 500, 'Internal Server Error')
         | 
| 1034 | 
            -
                  allow(Puppet::Network::HttpPool).to receive(:connection).with('myserver', 123, anything).and_return(double('request', get: response))
         | 
| 1035 1017 |  | 
| 1018 | 
            +
                  stub_request(:get, 'https://myserver:123/status/v1/simple/master').to_return(status: [500, "Internal Server Error"])
         | 
| 1019 | 
            +
             | 
| 1020 | 
            +
                  allow(Puppet).to receive(:debug)
         | 
| 1036 1021 | 
             
                  expect(Puppet).to receive(:debug).with("Puppet server myserver:123 is unavailable: 500 Internal Server Error")
         | 
| 1037 | 
            -
             | 
| 1022 | 
            +
             | 
| 1023 | 
            +
                  expect {
         | 
| 1024 | 
            +
                    configurer.run
         | 
| 1025 | 
            +
                  }.to raise_error(Puppet::Error, /Could not select a functional puppet master from server_list:/)
         | 
| 1038 1026 | 
             
                end
         | 
| 1039 1027 |  | 
| 1040 1028 | 
             
                it "should error when no servers in 'server_list' are reachable" do
         | 
| 1041 | 
            -
                  Puppet.settings[:server_list] =  | 
| 1042 | 
            -
                  error = Net::HTTPError.new(400, 'dummy server communication error')
         | 
| 1043 | 
            -
                  allow(Puppet::Network::HttpPool).to receive(:connection).with('myserver', 123, anything).and_return(double('request', get: error))
         | 
| 1029 | 
            +
                  Puppet.settings[:server_list] = "myserver:123,someotherservername"
         | 
| 1044 1030 |  | 
| 1045 | 
            -
                   | 
| 1046 | 
            -
                   | 
| 1047 | 
            -
             | 
| 1031 | 
            +
                  stub_request(:get, 'https://myserver:123/status/v1/simple/master').to_return(status: 400)
         | 
| 1032 | 
            +
                  stub_request(:get, 'https://someotherservername:8140/status/v1/simple/master').to_return(status: 400)
         | 
| 1033 | 
            +
             | 
| 1034 | 
            +
                  expect{
         | 
| 1035 | 
            +
                    configurer.run
         | 
| 1036 | 
            +
                  }.to raise_error(Puppet::Error, /Could not select a functional puppet master from server_list: 'myserver:123,someotherservername'/)
         | 
| 1048 1037 | 
             
                end
         | 
| 1049 1038 |  | 
| 1050 1039 | 
             
                it "should not make multiple node requests when the server is found" do
         | 
| 1051 1040 | 
             
                  Puppet.settings[:server_list] = ["myserver:123"]
         | 
| 1052 | 
            -
                  response = Net::HTTPOK.new(nil, 200, 'OK')
         | 
| 1053 1041 |  | 
| 1054 | 
            -
                   | 
| 1055 | 
            -
                   | 
| 1042 | 
            +
                  Puppet::Node.indirection.terminus_class = :rest
         | 
| 1043 | 
            +
                  Puppet::Resource::Catalog.indirection.terminus_class = :rest
         | 
| 1044 | 
            +
             | 
| 1045 | 
            +
                  stub_request(:get, 'https://myserver:123/status/v1/simple/master').to_return(status: 200)
         | 
| 1046 | 
            +
                  stub_request(:post, %r{https://myserver:123/puppet/v3/catalog}).to_return(status: 200)
         | 
| 1047 | 
            +
                  node_request = stub_request(:get, %r{https://myserver:123/puppet/v3/node/}).to_return(status: 200)
         | 
| 1048 | 
            +
             | 
| 1049 | 
            +
                  configurer.run
         | 
| 1056 1050 |  | 
| 1057 | 
            -
                   | 
| 1051 | 
            +
                  expect(node_request).to have_been_requested.once
         | 
| 1058 1052 | 
             
                end
         | 
| 1059 1053 | 
             
              end
         | 
| 1060 1054 | 
             
            end
         |