Ancora.Output (ancora v1.0.0)

Copy Markdown View Source

The only stdout writer in ancora.

Gate tasks (spec.check, spec.validate) run inside gated/2, which classifies the outcome as :ok, :usage, :env, or :internal. The first three emit a verdict via Ancora.Output.Verdict; :internal re-raises with no verdict line. Report tasks use the same wrapper for error paths and print the message without a verdict.

[CONFIG] diagnostics and Logger output go to stderr. Formatters other than the verdict emitter never produce the substring result=.

Summary

Functions

Branch summary branch base=<ref> changed_files=<N> findings=<N> (error=E warning=W info=I, info hidden).

Summary line checked subjects=<N> requirements=<N> errors=<E> warnings=<W>.

Write a [CONFIG] diagnostic to stderr. Never stdout.

Format one finding as [SEV] <subject> <code> <file> :: <message>.

Run fun inside the single emission wrapper.

Guidance line branch impacted_subjects=….

Guidance line branch next=….

JSON encoding of a report map, sanitized so it cannot contain result=.

Pin the default Logger handler to stderr.

Write one line to stdout.

The read-protocol sentence quoted by mix help spec.check and spec.prime's loop footer.

Warnings first, then info, then errors last. Stable within a band.

Functions

branch_summary(branch)

@spec branch_summary(map()) :: String.t()

Branch summary branch base=<ref> changed_files=<N> findings=<N> (error=E warning=W info=I, info hidden).

checked_summary(summary)

@spec checked_summary(map()) :: String.t()

Summary line checked subjects=<N> requirements=<N> errors=<E> warnings=<W>.

config_diagnostic(message)

@spec config_diagnostic(String.t()) :: :ok

Write a [CONFIG] diagnostic to stderr. Never stdout.

finding_line(finding)

@spec finding_line(Ancora.Finding.t()) :: String.t()

Format one finding as [SEV] <subject> <code> <file> :: <message>.

gated(task_name, fun)

@spec gated(String.t(), (-> term())) :: :ok | no_return()

Run fun inside the single emission wrapper.

fun must return {:ok, report}, {:usage, message}, {:env, message}, or {:internal, exception}. Any raised exception is classified :internal and re-raised with no verdict.

guidance_impacted(subjects)

@spec guidance_impacted([String.t()] | String.t()) :: String.t()

Guidance line branch impacted_subjects=….

guidance_next(command)

@spec guidance_next(String.t()) :: String.t()

Guidance line branch next=….

json_payload(report)

@spec json_payload(map()) :: String.t()

JSON encoding of a report map, sanitized so it cannot contain result=.

pin_logger_to_stderr()

@spec pin_logger_to_stderr() :: :ok

Pin the default Logger handler to stderr.

logger_std_h refuses a type change on a live handler, so this removes and re-adds :default when it is currently writing to standard_io.

puts(line)

@spec puts(String.t()) :: :ok

Write one line to stdout.

The read-protocol sentence is written verbatim (it names result= as documentation). Every other line is sanitized so it cannot contain result=.

read_protocol()

@spec read_protocol() :: String.t()

The read-protocol sentence quoted by mix help spec.check and spec.prime's loop footer.

sort_findings(findings)

@spec sort_findings([Ancora.Finding.t()]) :: [Ancora.Finding.t()]

Warnings first, then info, then errors last. Stable within a band.