Documentation
¶
Overview ¶
Package ci defines TerraCI's CI-facing domain: persisted plan/report artifacts, review-comment contracts, and provider-shared CI config types.
Index ¶
- Constants
- func DiffManagedLabels(previous, current []string) (add, remove []string)
- func EmbedManagedLabels(body string, labels []string) string
- func EncodeManagedLabelsMetadata(labels []string) string
- func ExtractManagedLabels(body string) []string
- func HasCommentMarker(body string) bool
- func NormalizeManagedLabels(labels []string) []string
- func PublishArtifacts(ctx context.Context, req PublishArtifactsRequest) error
- func ReportFilename(producer string) string
- func ResultFilename(producer string) string
- func StripManagedLabelsMetadata(body string) string
- type ArtifactContext
- type ArtifactContextOptions
- type ArtifactReportBuilder
- type ArtifactRun
- type ArtifactRunOptions
- type ArtifactWriter
- type CommentService
- type Image
- type ManagedLabelService
- type PlanResult
- type PlanResultCollection
- type PlanStatus
- type PublishArtifactsRequest
- type RenderBlock
- type RenderBlockKind
- type RenderDetails
- type RenderSection
- type RenderTable
- type RenderedReportOptions
- type RenderedSectionOptions
- type Report
- type ReportFreshness
- type ReportFreshnessStatus
- type ReportProvenance
- type ReportPublisher
- type ReportReader
- type ReportSection
- func (s ReportSection) Clone() ReportSection
- func (s ReportSection) Kind() ReportSectionKind
- func (s ReportSection) MarshalJSON() ([]byte, error)
- func (s ReportSection) Status() ReportStatus
- func (s ReportSection) Summary() string
- func (s ReportSection) Title() string
- func (s *ReportSection) UnmarshalJSON(data []byte) error
- type ReportSectionKind
- type ReportSelection
- type ReportSelectionOptions
- type ReportStatus
- type ReportStore
Examples ¶
Constants ¶
const CommentMarker = "<!-- terraci-plan-comment -->"
CommentMarker is used to identify TerraCI review comments for updates.
Variables ¶
This section is empty.
Functions ¶
func DiffManagedLabels ¶ added in v0.10.5
DiffManagedLabels computes provider label operations for TerraCI-owned labels.
func EmbedManagedLabels ¶ added in v0.10.5
EmbedManagedLabels records the labels currently owned by TerraCI in the review comment body. The encoded payload is intentionally hidden in an HTML comment so providers can remove only labels TerraCI created earlier.
func EncodeManagedLabelsMetadata ¶ added in v0.10.5
EncodeManagedLabelsMetadata serializes labels into a hidden comment payload.
func ExtractManagedLabels ¶ added in v0.10.5
ExtractManagedLabels returns the TerraCI-owned labels recorded in a comment body.
func HasCommentMarker ¶ added in v0.9.4
HasCommentMarker reports whether the provided body contains the TerraCI review-comment marker.
func NormalizeManagedLabels ¶ added in v0.10.5
NormalizeManagedLabels trims labels, removes empty entries, deduplicates them, and returns deterministic case-preserving order.
func PublishArtifacts ¶ added in v0.10.5
func PublishArtifacts(ctx context.Context, req PublishArtifactsRequest) error
PublishArtifacts persists raw producer results and replaces the matching render-ready report. Raw results are always passed to the writer. If report construction fails or returns nil, a nil report is written so stale report artifacts for the producer are removed.
func ReportFilename ¶ added in v0.9.0
ReportFilename returns the canonical artifact name for a producer's report.
func ResultFilename ¶ added in v0.10.3
ResultFilename returns the canonical artifact name for a producer's raw result.
func StripManagedLabelsMetadata ¶ added in v0.10.5
StripManagedLabelsMetadata removes all TerraCI managed-label metadata comments.
Types ¶
type ArtifactContext ¶ added in v0.10.5
type ArtifactContext struct {
ServiceDir string
WorkDir string
CommitSHA string
PipelineID string
PlanResultsFingerprint string
GeneratedAt time.Time
}
ArtifactContext describes the current artifact-producing run. Producers pass it to NewRenderedReport so provenance is derived consistently for every persisted report.
func NewArtifactContext ¶ added in v0.10.5
func NewArtifactContext(opts ArtifactContextOptions) ArtifactContext
NewArtifactContext normalizes run metadata used by report producers.
func (ArtifactContext) Provenance ¶ added in v0.10.5
func (c ArtifactContext) Provenance() *ReportProvenance
Provenance converts the artifact context into persisted report provenance.
type ArtifactContextOptions ¶ added in v0.10.5
type ArtifactContextOptions struct {
ServiceDir string
WorkDir string
CommitSHA string
PipelineID string
PlanResultsFingerprint string
GeneratedAt time.Time
}
ArtifactContextOptions describes how to construct an ArtifactContext.
type ArtifactReportBuilder ¶ added in v0.10.5
ArtifactReportBuilder builds a render-ready report for a producer artifact write. Returning nil without an error intentionally removes any stale report while still preserving raw results.
type ArtifactRun ¶ added in v0.10.5
type ArtifactRun struct {
Producer string
Artifact ArtifactContext
PlanResults *PlanResultCollection
}
ArtifactRun describes one producer's report/result artifact write.
func NewArtifactRun ¶ added in v0.10.5
func NewArtifactRun(opts ArtifactRunOptions) (ArtifactRun, error)
NewArtifactRun normalizes producer run metadata. When PlanResults is present and the artifact context has no explicit fingerprint, the plan collection fingerprint is used. Empty fingerprints remain valid for non-plan producers.
type ArtifactRunOptions ¶ added in v0.10.5
type ArtifactRunOptions struct {
Producer string
Artifact ArtifactContext
PlanResults *PlanResultCollection
}
ArtifactRunOptions describes how to construct an ArtifactRun.
type ArtifactWriter ¶ added in v0.10.5
type ArtifactWriter interface {
SaveResults(ctx context.Context, producer string, results any) error
ReplaceResultsAndReport(ctx context.Context, producer string, results any, report *Report) error
}
ArtifactWriter persists producer result/report artifacts.
type CommentService ¶
type CommentService interface {
IsEnabled() bool
UpsertComment(ctx context.Context, body string) error
}
CommentService defines the interface for posting plan summaries to PRs/MRs
type Image ¶ added in v0.9.4
type Image struct {
// Name is the image name (e.g., "hashicorp/terraform:1.6")
Name string `yaml:"name,omitempty" json:"name,omitempty" jsonschema:"description=Docker image name"`
// Entrypoint overrides the default entrypoint.
Entrypoint []string `yaml:"entrypoint,omitempty" json:"entrypoint,omitempty" jsonschema:"description=Override default entrypoint"`
}
Image defines a Docker image configuration for CI jobs.
func (*Image) HasEntrypoint ¶ added in v0.9.4
HasEntrypoint returns true if entrypoint is configured.
func (Image) MarshalYAML ¶ added in v0.10.0
MarshalYAML emits the short string form ("image:1.0") when only Name is set, preserving round-trip symmetry with UnmarshalYAML. Configs that started as shorthand stay shorthand after `terraci init` writes them back; only configs with an Entrypoint override expand to the full mapping.
type ManagedLabelService ¶ added in v0.10.5
type ManagedLabelService interface {
CurrentCommentBody(ctx context.Context) (body string, found bool, err error)
SyncLabels(ctx context.Context, previous, current []string) error
}
ManagedLabelService is an optional extension for comment services that can synchronize labels owned by the TerraCI summary comment.
type PlanResult ¶
type PlanResult struct {
ModuleID string `json:"module_id"`
ModulePath string `json:"module_path"`
Components map[string]string `json:"components,omitempty"`
Status PlanStatus `json:"status"`
Summary string `json:"summary"`
StructuredDetails string `json:"structured_details,omitempty"`
RawPlanOutput string `json:"raw_plan_output,omitempty"`
Error string `json:"error,omitempty"`
ExitCode int `json:"exit_code,omitempty"`
Duration time.Duration `json:"duration,omitempty"`
}
PlanResult is the canonical representation of a single module's plan outcome — both for in-memory rendering and on-disk persistence.
func (*PlanResult) Get ¶
func (r *PlanResult) Get(name string) string
Get returns the value of a named component from the Components map.
type PlanResultCollection ¶
type PlanResultCollection struct {
Results []PlanResult `json:"results"`
PipelineID string `json:"pipeline_id,omitempty"`
CommitSHA string `json:"commit_sha,omitempty"`
GeneratedAt time.Time `json:"generated_at"`
}
PlanResultCollection is the persisted CI artifact collection for a pipeline run.
func (*PlanResultCollection) Fingerprint ¶ added in v0.10.0
func (c *PlanResultCollection) Fingerprint() string
Fingerprint returns a stable content fingerprint for the collection.
type PlanStatus ¶
type PlanStatus string
PlanStatus represents the status of a terraform plan.
const ( PlanStatusPending PlanStatus = "pending" PlanStatusRunning PlanStatus = "running" PlanStatusSuccess PlanStatus = "success" PlanStatusNoChanges PlanStatus = "no_changes" PlanStatusChanges PlanStatus = "changes" PlanStatusFailed PlanStatus = "failed" )
func PlanStatusFromPlan ¶ added in v0.7.4
func PlanStatusFromPlan(hasChanges bool) PlanStatus
PlanStatusFromPlan determines the CI plan status from a parsed plan.
type PublishArtifactsRequest ¶ added in v0.10.5
type PublishArtifactsRequest struct {
Producer string
Writer ArtifactWriter
Results any
BuildReport ArtifactReportBuilder
}
PublishArtifactsRequest describes one canonical producer artifact write.
type RenderBlock ¶ added in v0.10.5
type RenderBlock struct {
Kind RenderBlockKind `json:"kind"`
Title string `json:"title,omitempty"`
Text string `json:"text,omitempty"`
Items []string `json:"items,omitempty"`
Table *RenderTable `json:"table,omitempty"`
Details *RenderDetails `json:"details,omitempty"`
}
RenderBlock is a generic block used by markdown and CLI renderers.
func RenderDetailsBlock ¶ added in v0.10.5
func RenderDetailsBlock(summary, body, language string) RenderBlock
RenderDetailsBlock returns a collapsible detail render block.
func RenderListBlock ¶ added in v0.10.5
func RenderListBlock(title string, items []string) RenderBlock
RenderListBlock returns an ordered list of already formatted items.
func RenderTableBlock ¶ added in v0.10.5
func RenderTableBlock(title string, columns []string, rows [][]string) RenderBlock
RenderTableBlock returns an ordered table render block.
func RenderTextBlock ¶ added in v0.10.5
func RenderTextBlock(text string) RenderBlock
RenderTextBlock returns a paragraph-like render block.
func (RenderBlock) Validate ¶ added in v0.10.5
func (b RenderBlock) Validate() error
Validate verifies one render block.
type RenderBlockKind ¶ added in v0.10.5
type RenderBlockKind string
RenderBlockKind identifies one render-ready block type.
const ( RenderBlockKindText RenderBlockKind = "text" RenderBlockKindTable RenderBlockKind = "table" RenderBlockKindList RenderBlockKind = "list" RenderBlockKindDetails RenderBlockKind = "details" )
type RenderDetails ¶ added in v0.10.5
type RenderDetails struct {
Summary string `json:"summary"`
Body string `json:"body,omitempty"`
Language string `json:"language,omitempty"`
}
RenderDetails is a collapsible detail block.
func (RenderDetails) Validate ¶ added in v0.10.5
func (d RenderDetails) Validate() error
Validate verifies details shape.
type RenderSection ¶ added in v0.10.5
type RenderSection struct {
Blocks []RenderBlock `json:"blocks,omitempty"`
}
RenderSection is a plugin-produced, renderer-facing section body.
func DecodeRenderSection ¶ added in v0.10.5
func DecodeRenderSection(section ReportSection) (RenderSection, error)
DecodeRenderSection decodes and validates a render-ready report section.
func (RenderSection) Validate ¶ added in v0.10.5
func (s RenderSection) Validate() error
Validate verifies that all render blocks are well-formed.
type RenderTable ¶ added in v0.10.5
type RenderTable struct {
Columns []string `json:"columns"`
Rows [][]string `json:"rows,omitempty"`
}
RenderTable is an ordered table payload.
func (RenderTable) Validate ¶ added in v0.10.5
func (t RenderTable) Validate() error
Validate verifies table shape.
type RenderedReportOptions ¶ added in v0.10.5
type RenderedReportOptions struct {
Producer string
Title string
Status ReportStatus
Summary string
Artifact ArtifactContext
Sections []RenderedSectionOptions
}
RenderedReportOptions describes a complete producer report assembled from render-ready sections.
type RenderedSectionOptions ¶ added in v0.10.5
type RenderedSectionOptions struct {
Title string
Summary string
Status ReportStatus
Blocks []RenderBlock
}
RenderedSectionOptions describes one render-ready report section.
type Report ¶ added in v0.7.4
type Report struct {
Producer string `json:"producer"`
Title string `json:"title"`
Status ReportStatus `json:"status"`
Summary string `json:"summary"`
Provenance *ReportProvenance `json:"provenance,omitempty"`
Sections []ReportSection `json:"sections,omitempty"`
}
Report is a CI enrichment artifact written by a tool and consumed by report aggregation flows. Producers persist reports as {serviceDir}/{producer}-report.json.
func LoadReport ¶ added in v0.9.0
LoadReport reads and validates a single report file from disk. It is intended for low-level tests and store internals; producers should use ReportStore.
func NewRenderedReport ¶ added in v0.10.5
func NewRenderedReport(opts RenderedReportOptions) (*Report, error)
NewRenderedReport builds and validates a producer report from render-ready sections. Section statuses default to the report status when omitted.
Example ¶
package main
import (
"fmt"
"github.com/edelwud/terraci/pkg/ci"
)
func main() {
report, err := ci.NewRenderedReport(ci.RenderedReportOptions{
Producer: "policy",
Title: "Policy Check",
Status: ci.ReportStatusWarn,
Summary: "1 warning",
Artifact: ci.NewArtifactContext(ci.ArtifactContextOptions{
CommitSHA: "abc123",
PlanResultsFingerprint: "fingerprint",
}),
Sections: []ci.RenderedSectionOptions{{
Title: "Findings",
Summary: "1 warning",
Blocks: []ci.RenderBlock{
ci.RenderTableBlock("Warnings", []string{"Module", "Message"}, [][]string{{"svc/prod/vpc", "tag missing"}}),
},
}},
})
if err != nil {
panic(err)
}
fmt.Println(report.Producer, report.Sections[0].Kind())
}
Output: policy rendered
type ReportFreshness ¶ added in v0.10.5
type ReportFreshness struct {
Status ReportFreshnessStatus
Warning string
}
ReportFreshness is the freshness decision for one report.
func EvaluateReportFreshness ¶ added in v0.10.5
func EvaluateReportFreshness(collection *PlanResultCollection, report *Report, consumer string) ReportFreshness
EvaluateReportFreshness evaluates one report against the current plan collection.
type ReportFreshnessStatus ¶ added in v0.10.5
type ReportFreshnessStatus string
ReportFreshnessStatus describes whether a producer report belongs to the current plan-result collection.
const ( ReportFreshnessCurrent ReportFreshnessStatus = "current" ReportFreshnessDegraded ReportFreshnessStatus = "degraded" ReportFreshnessStale ReportFreshnessStatus = "stale" )
type ReportProvenance ¶ added in v0.10.0
type ReportProvenance struct {
GeneratedAt time.Time `json:"generated_at"`
CommitSHA string `json:"commit_sha,omitempty"`
PipelineID string `json:"pipeline_id,omitempty"`
PlanResultsFingerprint string `json:"plan_results_fingerprint,omitempty"`
}
ReportProvenance captures the source run identity for a persisted report.
Producers should populate provenance for every persisted report so local consumers (e.g. localexec/render) can decide whether the artifact still matches the current workspace. Producers should derive it from ArtifactContext instead of assembling it by hand.
type ReportPublisher ¶ added in v0.10.5
type ReportPublisher interface {
Publish(report *Report)
SaveReport(ctx context.Context, report *Report) error
}
ReportPublisher publishes renderer-ready producer reports.
type ReportReader ¶ added in v0.10.5
type ReportReader interface {
Get(producer string) (*Report, bool)
All() []*Report
LoadReports(ctx context.Context) ([]*Report, error)
}
ReportReader loads reports from the current process and/or service dir.
type ReportSection ¶ added in v0.10.0
type ReportSection struct {
// contains filtered or unexported fields
}
ReportSection is a neutral value object describing one slice of a CI report. Persisted producer reports must publish ReportSectionKindRendered payloads. Use NewRenderedSection or NewRenderedReport instead of constructing report JSON or payloads by hand.
func NewRenderedSection ¶ added in v0.10.5
func NewRenderedSection(opts RenderedSectionOptions) (ReportSection, error)
NewRenderedSection builds and validates a render-ready report section.
func (ReportSection) Clone ¶ added in v0.10.5
func (s ReportSection) Clone() ReportSection
Clone returns a defensive copy of the report section.
func (ReportSection) Kind ¶ added in v0.10.0
func (s ReportSection) Kind() ReportSectionKind
Kind returns the section payload shape.
func (ReportSection) MarshalJSON ¶ added in v0.10.5
func (s ReportSection) MarshalJSON() ([]byte, error)
MarshalJSON preserves the public persisted report section shape while keeping the in-process value object immutable from external packages.
func (ReportSection) Status ¶ added in v0.10.0
func (s ReportSection) Status() ReportStatus
Status returns the section status.
func (ReportSection) Summary ¶ added in v0.10.5
func (s ReportSection) Summary() string
Summary returns the short section summary.
func (ReportSection) Title ¶ added in v0.10.0
func (s ReportSection) Title() string
Title returns the section title.
func (*ReportSection) UnmarshalJSON ¶ added in v0.10.5
func (s *ReportSection) UnmarshalJSON(data []byte) error
UnmarshalJSON preserves the public persisted report section shape while keeping direct payload construction out of the Go API.
type ReportSectionKind ¶ added in v0.10.0
type ReportSectionKind string
ReportSectionKind identifies a report section payload shape. Summary-facing producer reports should use ReportSectionKindRendered so consumers can render plugin output without knowing the producer's domain model.
const ReportSectionKindRendered ReportSectionKind = "rendered"
ReportSectionKindRendered is the canonical render-ready report payload. It is intentionally generic: producer plugins own their domain model and publish only the view model needed by summary/local renderers.
type ReportSelection ¶ added in v0.10.5
ReportSelection is the canonical selected-report result for consumers.
func SelectCurrentReports ¶ added in v0.10.5
func SelectCurrentReports(collection *PlanResultCollection, reports []*Report, opts ReportSelectionOptions) ReportSelection
SelectCurrentReports selects reports safe to render for the supplied plan collection. Reports with missing provenance or fingerprints are considered degraded but renderable; reports with mismatched non-empty fingerprints are skipped and returned as warnings.
type ReportSelectionOptions ¶ added in v0.10.5
ReportSelectionOptions controls report freshness selection.
type ReportStatus ¶ added in v0.7.4
type ReportStatus string
ReportStatus indicates the outcome of a producer's check.
const ( ReportStatusPass ReportStatus = "pass" ReportStatusWarn ReportStatus = "warn" ReportStatusFail ReportStatus = "fail" )
func StatusFromCounts ¶ added in v0.10.0
func StatusFromCounts(fail, warn int) ReportStatus
StatusFromCounts returns the strictest status implied by the given fail / warn counts: any failure → Fail; any warning → Warn; otherwise Pass. Producers can still override (e.g. tfupdate treats "updates available" as a warning); this helper covers the common case.
func (ReportStatus) Valid ¶ added in v0.10.0
func (s ReportStatus) Valid() bool
Valid reports whether the status is one of the supported CI report outcomes.
type ReportStore ¶ added in v0.10.5
type ReportStore interface {
ReportPublisher
ReportReader
ArtifactWriter
}
ReportStore is the canonical producer/consumer boundary for CI reports. Memory stores support in-process exchange; file stores additionally persist artifacts using the canonical {producer}-report.json / {producer}-results.json filenames.
func NewFileReportStore ¶ added in v0.10.5
func NewFileReportStore(serviceDir string) ReportStore
NewFileReportStore creates a report store backed by serviceDir. It also keeps an in-memory overlay for reports published by in-process plugins.
func NewMemoryReportStore ¶ added in v0.10.5
func NewMemoryReportStore() ReportStore
NewMemoryReportStore creates an in-process report store.