30-second answer
m365-governance runIt plans, collects what the target can reach, evaluates the evidence and writes the report.
Why it exists
A tenant assessed end to end was ten collect commands and then an evaluate,
and the person running them had to know what a slice is before obtaining a first
result. Choosing among ten is a decision this engine can make from the target it
was given, and asking somebody to make it before they have seen a single finding
is asking them to learn the architecture in order to use the tool.
It says what it will not do, before it does anything
Plan: 10 of 11 collections
run sites every site this identity can enumerate
run owners who administers one site
…
not run conditional-access reads Microsoft Graph, and this engine never
acquires a token: set one to include it
A collection that was not attempted is not a resource that is not
there. Nothing below reads these, and no rule over the evidence
can recover what they would have said.Every collection appears with a verdict, including the ones that will not
happen. A run that quietly skipped half its slices would produce a report that
looks complete to the only person who could tell that it is not. It is the same
reason unknown is never a pass.
The plan also refuses what this machine cannot do. Without PowerShell 7 it plans nothing and says so, rather than promising ten collections it would refuse a moment later.
--dry-run prints the plan and reaches no tenant.
A collection that fails does not end the run
Six of fifty-three sites refusing a collector is a fact about coverage, not a
reason to produce nothing. Each collection carries its own manifest saying
whether it was completed, partial, failed or cancelled, and the report is
built over what was actually gathered.
Options
--project names the project file. Omit it to use the nearest
m365-governance.toml from here upwards, which is what
setup writes. Everything
below that the file already holds can be left out.
--client-id, --tenant-url and --site-url are the identity and
the target, as in setup.
--device-login signs in with a device code, for hosts with no browser.
--tenant-id, --certificate-path and --certificate-password-env
sign in as an application with a certificate instead of a person; the password
is the name of an environment variable, never the password.
--output is where the evidence is written. It is kept, because it is what
the conclusions were decided from, and a report without it cannot be checked.
--profile is a profile file; the packaged default selects every rule.
--rules is a directory of rule files, and it replaces the shipped rules
entirely rather than adding to them.
--format is markdown, json or html, and --out writes the report
there. --bundle writes one folder per run, holding the run document, the
evidence it was decided from and its report; nothing new is computed.
--fail-on is nothing, fail or unresolved, and exits 1 on findings.
unresolved counts unknown and invalid-evidence alongside fail.
--dry-run prints the plan and reaches no tenant.
What it does not do
It decides nothing a rule decides, it merges no evidence, and it does not make a
slice apply to a target it does not apply to. Every step in it is a command that
exists on its own: collect
for the parts, evaluate
for the reading, assess for
a document somebody else can check.