Project: Chef InSpec (Provisioning / Security & Compliance)
File: profile-evaluations.md

In this document following topics will be covered: How profiles are initialised? How profiles are evaluated in different InSpec CLI commands? Why do we load profile context? How runner is using rspec and running profile tests? Profiles are initialised using `Profile.forpath` method which is called via `Profile.fortarget` method which resolves the target and calls `Profile.for_fetcher` to fetch profile from a remote location using the fetcher object. Finally `Profile.forpath` is called via `Profile.forfetcher` method which creates a new instance of `Inspec::Profile` class for a given path by resolving the path. This is how profile is initialised while using InSpec profiles in InSpec commands like exec, archive, check, export and json. -- #1 Class.new(*args) at chef/inspec/lib/inspec/profile.rb:64 `inspec exec` Inspec exec calls runner run, which collect control control tests using Inspec::Profile.collect_tests by loading the control file and context via Inspec::ProfileContext. Inspec::Runner.run starts with initiates the running process of inspec profile execution. Inspec::Runner.load loads necessary dependencies for the process and control tests by calling Inspec::Profile.collect_tests. Inspec::Profile.collect_tests gathers the control tests from the profile. Inspec::ProfileContext.loadcontrolfile calls loadwithcontext to load control source in a context. Inspec::ProfileContext.loadwithcontext loads control source within profile context -- #3 Hash.each at chef/inspec/lib/inspec/profile.rb:247 -- #6 Hash.each at chef/inspec/lib/inspec/dependencies/dependency_set.rb:67 -- #10 Array.each at chef/inspec/lib/inspec/runner.rb:107 `inspec check` Inspec check command verifies the profile based on the metadata and params evaluated from the profile source code. It uses the loaded parameters which are evaluated and loaded within profile context. Inspec::Profile.check starts with performing a check of an InSpec profile. Inspec::Profile.controls_count determines the count of controls in the profile, needed for check summary. Inspec::Profile.params returns metadata and other needed parameters of an InSpec profile. Inspec::Profile.load_params loads the parameters associated with the profile. Inspec::Profile.loadchecksparams Inspec::Profile.collect_tests gathers the control tests from the profile. Inspec::ProfileContext.loadcontrolfile calls loadwithcontext to load control source in a context. Inspec::ProfileContext.loadwithcontext loads control source within profile context. -- #3 Hash.each at chef/inspec/lib/inspec/profile.rb:247 -- #6 Hash.each at

`inspec export` Inspec export command extracts our the information of a profile containing details of metadata of a profile and other parameters by evaluating the source code of the profile. It uses the loaded parameters which are evaluated and loaded within profile context. Inspec::Profile.info starts with gathering information or metadata about the InSpec profile. Inspec::Profile.params returns metadata and other needed parameters of an InSpec profile. Inspec::Profile.load_params loads the parameters associated with the profile. Inspec::Profile.loadchecksparams Inspec::Profile.collect_tests gathers the control tests from the profile. Inspec::ProfileContext.loadcontrolfile calls loadwithcontext to load control source in a context. Inspec::ProfileContext.loadwithcontext loads control source within profile context. -- #3 Hash.each at chef/inspec/lib/inspec/profile.rb:247 -- #6 Hash.each at chef/inspec/lib/inspec/dependencies/dependency_set.rb:67 `inspec archive` Inspec archive command checks the profile first and then the archive operation is followed. Inspec::Profile.check starts with performing a check of an InSpec profile. Inspec::Profile.controls_count determines the count of controls in the profile, needed for check summary. Inspec::Profile.params returns metadata and other needed parameters of an InSpec profile. Inspec::Profile.load_params loads the parameters associated with the profile. Inspec::Profile.loadchecksparams Inspec::Profile.collect_tests gathers the control tests from the profile. Inspec::ProfileContext.loadcontrolfile calls loadwithcontext to load control source in a context. Inspec::ProfileContext.loadwithcontext loads control source within profile context. -- #3 Hash.each at chef/inspec/lib/inspec/profile.rb:247 -- #6 Hash.each at chef/inspec/lib/inspec/dependencies/dependency_set.rb:67 The reason why loadwithcontext is used is because it is called and used by the collecttests method in the Inspec::Profile class to get control tests in a context. Because the collecttests method is responsible for collecting all of the controls defined in the profile. After collecting all control tests, test_collector collects tests defined in each control to run with rspec. The reason why we need to load controls is so that they can be executed as part of the InSpec profile. Inspec::Runner loads all the control tests via Inspec::Runner.load which is then run with Inspec::Runner.run_tests. And then the tests defined in each control is provided to test collector (RunnerRspec object) which runs the tests using Rspec.