
// This file was autogenerated by go-to-protobuf. Do not edit it manually!

syntax = "proto2";

package github.com.akuity.kargo.api.v1alpha1;

import "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1/generated.proto";
import "k8s.io/apimachinery/pkg/apis/meta/v1/generated.proto";
import "k8s.io/apimachinery/pkg/runtime/generated.proto";
import "k8s.io/apimachinery/pkg/runtime/schema/generated.proto";

// Package-wide variables from generator "generated".
option go_package = "github.com/akuity/kargo/api/v1alpha1";

// AnalysisRunArgument represents an argument to be added to an AnalysisRun.
message AnalysisRunArgument {
  // Name is the name of the argument.
  //
  // +kubebuilder:validation:Required
  optional string name = 1;

  // Value is the value of the argument.
  //
  // +kubebuilder:validation:Required
  optional string value = 2;
}

// AnalysisRunMetadata contains optional metadata that should be applied to all
// AnalysisRuns.
message AnalysisRunMetadata {
  // Additional labels to apply to an AnalysisRun.
  map<string, string> labels = 1;

  // Additional annotations to apply to an AnalysisRun.
  map<string, string> annotations = 2;
}

// AnalysisRunReference is a reference to an AnalysisRun.
message AnalysisRunReference {
  // Namespace is the namespace of the AnalysisRun.
  optional string namespace = 1;

  // Name is the name of the AnalysisRun.
  optional string name = 2;

  // Phase is the last observed phase of the AnalysisRun referenced by Name.
  optional string phase = 3;
}

// AnalysisTemplateReference is a reference to an AnalysisTemplate.
message AnalysisTemplateReference {
  // Name is the name of the AnalysisTemplate in the same project/namespace as
  // the Stage.
  //
  // +kubebuilder:validation:Required
  optional string name = 1;
}

// ApprovedStage describes a Stage for which Freight has been (manually)
// approved.
message ApprovedStage {
}

// ArgoCDAppHealthStatus describes the health of an ArgoCD Application.
message ArgoCDAppHealthStatus {
  optional string status = 1;

  optional string message = 2;
}

// ArgoCDAppStatus describes the current state of a single ArgoCD Application.
message ArgoCDAppStatus {
  // Namespace is the namespace of the ArgoCD Application.
  optional string namespace = 1;

  // Name is the name of the ArgoCD Application.
  optional string name = 2;

  // HealthStatus is the health of the ArgoCD Application.
  optional ArgoCDAppHealthStatus healthStatus = 3;

  // SyncStatus is the sync status of the ArgoCD Application.
  optional ArgoCDAppSyncStatus syncStatus = 4;
}

// ArgoCDAppSyncStatus describes the sync status of an ArgoCD Application.
message ArgoCDAppSyncStatus {
  optional string status = 1;

  optional string revision = 2;

  repeated string revisions = 3;
}

// Chart describes a specific version of a Helm chart.
message Chart {
  // RepoURL specifies the URL of a Helm chart repository. Classic chart
  // repositories (using HTTP/S) can contain differently named charts. When this
  // field points to such a repository, the Name field will specify the name of
  // the chart within the repository. In the case of a repository within an OCI
  // registry, the URL implicitly points to a specific chart and the Name field
  // will be empty.
  optional string repoURL = 1;

  // Name specifies the name of the chart.
  optional string name = 2;

  // Version specifies a particular version of the chart.
  optional string version = 3;
}

// ChartDiscoveryResult represents the result of a chart discovery operation for
// a ChartSubscription.
message ChartDiscoveryResult {
  // RepoURL is the repository URL of the Helm chart, as specified in the
  // ChartSubscription.
  //
  // +kubebuilder:validation:MinLength=1
  optional string repoURL = 1;

  // Name is the name of the Helm chart, as specified in the ChartSubscription.
  optional string name = 2;

  // SemverConstraint is the constraint for which versions were discovered.
  // This field is optional, and only populated if the ChartSubscription
  // specifies a SemverConstraint.
  optional string semverConstraint = 3;

  // Versions is a list of versions discovered by the Warehouse for the
  // ChartSubscription. An empty list indicates that the discovery operation was
  // successful, but no versions matching the ChartSubscription criteria were
  // found.
  //
  // +optional
  repeated string versions = 4;
}

// ChartSubscription defines a subscription to a Helm chart repository.
message ChartSubscription {
  // RepoURL specifies the URL of a Helm chart repository. It may be a classic
  // chart repository (using HTTP/S) OR a repository within an OCI registry.
  // Classic chart repositories can contain differently named charts. When this
  // field points to such a repository, the Name field MUST also be used
  // to specify the name of the desired chart within that repository. In the
  // case of a repository within an OCI registry, the URL implicitly points to
  // a specific chart and the Name field MUST NOT be used. The RepoURL field is
  // required.
  //
  // +kubebuilder:validation:MinLength=1
  // +kubebuilder:validation:Pattern=`^(((https?)|(oci))://)([\w\d\.\-]+)(:[\d]+)?(/.*)*$`
  optional string repoURL = 1;

  // Name specifies the name of a Helm chart to subscribe to within a classic
  // chart repository specified by the RepoURL field. This field is required
  // when the RepoURL field points to a classic chart repository and MUST
  // otherwise be empty.
  optional string name = 2;

  // SemverConstraint specifies constraints on what new chart versions are
  // permissible. This field is optional. When left unspecified, there will be
  // no constraints, which means the latest version of the chart will always be
  // used. Care should be taken with leaving this field unspecified, as it can
  // lead to the unanticipated rollout of breaking changes.
  // More info: https://github.com/masterminds/semver#checking-version-constraints
  //
  // +kubebuilder:validation:Optional
  optional string semverConstraint = 3;

  // DiscoveryLimit is an optional limit on the number of chart versions that
  // can be discovered for this subscription. The limit is applied after
  // filtering charts based on the SemverConstraint field.
  // When left unspecified, the field is implicitly treated as if its value
  // were "20". The upper limit for this field is 100.
  //
  // +kubebuilder:validation:Minimum=1
  // +kubebuilder:validation:Maximum=100
  // +kubebuilder:default=20
  optional int32 discoveryLimit = 4;
}

// DiscoveredArtifacts holds the artifacts discovered by the Warehouse for its
// subscriptions.
message DiscoveredArtifacts {
  // DiscoveredAt is the time at which the Warehouse discovered the artifacts.
  //
  // +optional
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.Time discoveredAt = 4;

  // Git holds the commits discovered by the Warehouse for the Git
  // subscriptions.
  //
  // +optional
  repeated GitDiscoveryResult git = 1;

  // Images holds the image references discovered by the Warehouse for the
  // image subscriptions.
  //
  // +optional
  repeated ImageDiscoveryResult images = 2;

  // Charts holds the charts discovered by the Warehouse for the chart
  // subscriptions.
  //
  // +optional
  repeated ChartDiscoveryResult charts = 3;
}

// DiscoveredCommit represents a commit discovered by a Warehouse for a
// GitSubscription.
message DiscoveredCommit {
  // ID is the identifier of the commit. This typically is a SHA-1 hash.
  //
  // +kubebuilder:validation:MinLength=1
  optional string id = 1;

  // Branch is the branch in which the commit was found. This field is
  // optional, and populated based on the CommitSelectionStrategy of the
  // GitSubscription.
  optional string branch = 2;

  // Tag is the tag that resolved to this commit. This field is optional, and
  // populated based on the CommitSelectionStrategy of the GitSubscription.
  optional string tag = 3;

  // Subject is the subject of the commit (i.e. the first line of the commit
  // message).
  optional string subject = 4;

  // Author is the author of the commit.
  optional string author = 5;

  // Committer is the person who committed the commit.
  optional string committer = 6;

  // CreatorDate is the commit creation date as specified by the commit, or
  // the tagger date if the commit belongs to an annotated tag.
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.Time creatorDate = 7;
}

// DiscoveredImageReference represents an image reference discovered by a
// Warehouse for an ImageSubscription.
message DiscoveredImageReference {
  // Tag is the tag of the image.
  //
  // +kubebuilder:validation:MinLength=1
  // +kubebuilder:validation:MaxLength=128
  // +kubebuilder:validation:Pattern=`^[\w.\-\_]+$`
  optional string tag = 1;

  // Digest is the digest of the image.
  //
  // +kubebuilder:validation:MinLength=1
  // +kubebuilder:validation:Pattern=`^[a-z0-9]+:[a-f0-9]+$`
  optional string digest = 2;

  // GitRepoURL is the URL of the Git repository that contains the source
  // code for this image. This field is optional, and only populated if the
  // ImageSubscription specifies a GitRepoURL.
  optional string gitRepoURL = 3;

  // CreatedAt is the time the image was created. This field is optional, and
  // not populated for every ImageSelectionStrategy.
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.Time createdAt = 4;
}

// Freight represents a collection of versioned artifacts.
message Freight {
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.ObjectMeta metadata = 1;

  // Alias is a human-friendly alias for a piece of Freight. This is an optional
  // field. A defaulting webhook will sync this field with the value of the
  // kargo.akuity.io/alias label. When the alias label is not present or differs
  // from the value of this field, the defaulting webhook will set the label to
  // the value of this field. If the alias label is present and this field is
  // empty, the defaulting webhook will set the value of this field to the value
  // of the alias label. If this field is empty and the alias label is not
  // present, the defaulting webhook will choose an available alias and assign
  // it to both the field and label.
  optional string alias = 7;

  // Origin describes a kind of Freight in terms of its origin.
  //
  // +kubebuilder:validation:Required
  optional FreightOrigin origin = 9;

  // Commits describes specific Git repository commits.
  repeated GitCommit commits = 3;

  // Images describes specific versions of specific container images.
  repeated Image images = 4;

  // Charts describes specific versions of specific Helm charts.
  repeated Chart charts = 5;

  // Status describes the current status of this Freight.
  optional FreightStatus status = 6;
}

// FreightCollection is a collection of FreightReferences, each of which
// represents a piece of Freight that has been selected for deployment to a
// Stage.
message FreightCollection {
  // ID is a unique and deterministically calculated identifier for the
  // FreightCollection. It is updated on each use of the UpdateOrPush method.
  optional string id = 3;

  // Freight is a map of FreightReference objects, indexed by their Warehouse
  // origin.
  map<string, FreightReference> items = 1;

  // VerificationHistory is a stack of recent VerificationInfo. By default,
  // the last ten VerificationInfo are stored.
  repeated VerificationInfo verificationHistory = 2;
}

// FreightList is a list of Freight resources.
message FreightList {
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.ListMeta metadata = 1;

  repeated Freight items = 2;
}

// FreightOrigin describes a kind of Freight in terms of where it may have
// originated.
//
// +protobuf.options.(gogoproto.goproto_stringer)=false
message FreightOrigin {
  // Kind is the kind of resource from which Freight may have originated. At
  // present, this can only be "Warehouse".
  //
  // +kubebuilder:validation:Required
  optional string kind = 1;

  // Name is the name of the resource of the kind indicated by the Kind field
  // from which Freight may originated.
  //
  // +kubebuilder:validation:Required
  optional string name = 2;
}

// FreightReference is a simplified representation of a piece of Freight -- not
// a root resource type.
message FreightReference {
  // Name is system-assigned identifier that is derived deterministically from
  // the contents of the Freight. i.e. Two pieces of Freight can be compared for
  // equality by comparing their Names.
  optional string name = 1;

  // Origin describes a kind of Freight in terms of its origin.
  optional FreightOrigin origin = 8;

  // Commits describes specific Git repository commits.
  repeated GitCommit commits = 2;

  // Images describes specific versions of specific container images.
  repeated Image images = 3;

  // Charts describes specific versions of specific Helm charts.
  repeated Chart charts = 4;
}

// FreightRequest expresses a Stage's need for Freight having originated from a
// particular Warehouse.
message FreightRequest {
  // Origin specifies from where the requested Freight must have originated.
  // This is a required field.
  //
  // +kubebuilder:validation:Required
  optional FreightOrigin origin = 1;

  // Sources describes where the requested Freight may be obtained from. This is
  // a required field.
  optional FreightSources sources = 2;
}

message FreightSources {
  // Direct indicates the requested Freight may be obtained directly from the
  // Warehouse from which it originated. If this field's value is false, then
  // the value of the Stages field must be non-empty. i.e. Between the two
  // fields, at least one source must be specified.
  optional bool direct = 1;

  // Stages identifies other "upstream" Stages as potential sources of the
  // requested Freight. If this field's value is empty, then the value of the
  // Direct field must be true. i.e. Between the two fields, at least on source
  // must be specified.
  repeated string stages = 2;
}

// FreightStatus describes a piece of Freight's most recently observed state.
message FreightStatus {
  // VerifiedIn describes the Stages in which this Freight has been verified
  // through promotion and subsequent health checks.
  map<string, VerifiedStage> verifiedIn = 1;

  // ApprovedFor describes the Stages for which this Freight has been approved
  // preemptively/manually by a user. This is useful for hotfixes, where one
  // might wish to promote a piece of Freight to a given Stage without
  // transiting the entire pipeline.
  map<string, ApprovedStage> approvedFor = 2;
}

// GitCommit describes a specific commit from a specific Git repository.
message GitCommit {
  // RepoURL is the URL of a Git repository.
  optional string repoURL = 1;

  // ID is the ID of a specific commit in the Git repository specified by
  // RepoURL.
  optional string id = 2;

  // Branch denotes the branch of the repository where this commit was found.
  optional string branch = 3;

  // Tag denotes a tag in the repository that matched selection criteria and
  // resolved to this commit.
  optional string tag = 4;

  // Message is the message associated with the commit. At present, this only
  // contains the first line (subject) of the commit message.
  optional string message = 6;

  // Author is the author of the commit.
  optional string author = 7;

  // Committer is the person who committed the commit.
  optional string committer = 8;
}

// GitDiscoveryResult represents the result of a Git discovery operation for a
// GitSubscription.
message GitDiscoveryResult {
  // RepoURL is the repository URL of the GitSubscription.
  //
  // +kubebuilder:validation:MinLength=1
  // +kubebuilder:validation:Pattern=`(?:^(https?)://(?:([\w-]+):(.+)@)?([\w-]+(?:\.[\w-]+)*)(?::(\d{1,5}))?(/.*)$)|(?:^([\w-]+)@([\w+]+(?:\.[\w-]+)*):(/?.*))`
  optional string repoURL = 1;

  // Commits is a list of commits discovered by the Warehouse for the
  // GitSubscription. An empty list indicates that the discovery operation was
  // successful, but no commits matching the GitSubscription criteria were found.
  //
  // +optional
  repeated DiscoveredCommit commits = 2;
}

// GitSubscription defines a subscription to a Git repository.
message GitSubscription {
  // URL is the repository's URL. This is a required field.
  //
  // +kubebuilder:validation:MinLength=1
  // +kubebuilder:validation:Pattern=`(?:^(https?)://(?:([\w-]+):(.+)@)?([\w-]+(?:\.[\w-]+)*)(?::(\d{1,5}))?(/.*)$)|(?:^([\w-]+)@([\w+]+(?:\.[\w-]+)*):(/?.*))`
  optional string repoURL = 1;

  // CommitSelectionStrategy specifies the rules for how to identify the newest
  // commit of interest in the repository specified by the RepoURL field. This
  // field is optional. When left unspecified, the field is implicitly treated
  // as if its value were "NewestFromBranch".
  // Accepted values: Lexical, NewestFromBranch, NewestTag, SemVer
  //
  // +kubebuilder:default=NewestFromBranch
  optional string commitSelectionStrategy = 2;

  // Branch references a particular branch of the repository. The value in this
  // field only has any effect when the CommitSelectionStrategy is
  // NewestFromBranch or left unspecified (which is implicitly the same as
  // NewestFromBranch). This field is optional. When left unspecified, (and the
  // CommitSelectionStrategy is NewestFromBranch or unspecified), the
  // subscription is implicitly to the repository's default branch.
  //
  // +kubebuilder:validation:MinLength=1
  // +kubebuilder:validation:Pattern=`^\w+([-/]\w+)*$`
  optional string branch = 3;

  // StrictSemvers specifies whether only "strict" semver tags should be
  // considered. A "strict" semver tag is one containing ALL of major, minor,
  // and patch version components. This is enabled by default, but only has any
  // effect when the CommitSelectionStrategy is SemVer. This should be disabled
  // cautiously, as it creates the potential for any tag containing numeric
  // characters only to be mistaken for a semver string containing the major
  // version number only.
  //
  // +kubebuilder:default=true
  optional bool strictSemvers = 11;

  // SemverConstraint specifies constraints on what new tagged commits are
  // considered in determining the newest commit of interest. The value in this
  // field only has any effect when the CommitSelectionStrategy is SemVer. This
  // field is optional. When left unspecified, there will be no constraints,
  // which means the latest semantically tagged commit will always be used. Care
  // should be taken with leaving this field unspecified, as it can lead to the
  // unanticipated rollout of breaking changes.
  //
  // +kubebuilder:validation:Optional
  optional string semverConstraint = 4;

  // AllowTags is a regular expression that can optionally be used to limit the
  // tags that are considered in determining the newest commit of interest. The
  // value in this field only has any effect when the CommitSelectionStrategy is
  // Lexical, NewestTag, or SemVer. This field is optional.
  //
  // +kubebuilder:validation:Optional
  optional string allowTags = 5;

  // IgnoreTags is a list of tags that must be ignored when determining the
  // newest commit of interest. No regular expressions or glob patterns are
  // supported yet. The value in this field only has any effect when the
  // CommitSelectionStrategy is Lexical, NewestTag, or SemVer. This field is
  // optional.
  //
  // +kubebuilder:validation:Optional
  repeated string ignoreTags = 6;

  // InsecureSkipTLSVerify specifies whether certificate verification errors
  // should be ignored when connecting to the repository. This should be enabled
  // only with great caution.
  optional bool insecureSkipTLSVerify = 7;

  // IncludePaths is a list of selectors that designate paths in the repository
  // that should trigger the production of new Freight when changes are detected
  // therein. When specified, only changes in the identified paths will trigger
  // Freight production. When not specified, changes in any path will trigger
  // Freight production. Selectors may be defined using:
  //   1. Exact paths to files or directories (ex. "charts/foo")
  //   2. Glob patterns (prefix the pattern with "glob:"; ex. "glob:*.yaml")
  //   3. Regular expressions (prefix the pattern with "regex:" or "regexp:";
  //      ex. "regexp:^.*\.yaml$")
  // Paths selected by IncludePaths may be unselected by ExcludePaths. This
  // is a useful method for including a broad set of paths and then excluding a
  // subset of them.
  // +kubebuilder:validation:Optional
  repeated string includePaths = 8;

  // ExcludePaths is a list of selectors that designate paths in the repository
  // that should NOT trigger the production of new Freight when changes are
  // detected therein. When specified, changes in the identified paths will not
  // trigger Freight production. When not specified, paths that should trigger
  // Freight production will be defined solely by IncludePaths. Selectors may be
  // defined using:
  //   1. Exact paths to files or directories (ex. "charts/foo")
  //   2. Glob patterns (prefix the pattern with "glob:"; ex. "glob:*.yaml")
  //   3. Regular expressions (prefix the pattern with "regex:" or "regexp:";
  //      ex. "regexp:^.*\.yaml$")
  // Paths selected by IncludePaths may be unselected by ExcludePaths. This
  // is a useful method for including a broad set of paths and then excluding a
  // subset of them.
  // +kubebuilder:validation:Optional
  repeated string excludePaths = 9;

  // DiscoveryLimit is an optional limit on the number of commits that can be
  // discovered for this subscription. The limit is applied after filtering
  // commits based on the AllowTags and IgnoreTags fields.
  // When left unspecified, the field is implicitly treated as if its value
  // were "20". The upper limit for this field is 100.
  //
  // +kubebuilder:validation:Minimum=1
  // +kubebuilder:validation:Maximum=100
  // +kubebuilder:default=20
  optional int32 discoveryLimit = 10;
}

// Health describes the health of a Stage.
message Health {
  // Status describes the health of the Stage.
  optional string status = 1;

  // Issues clarifies why a Stage in any state other than Healthy is in that
  // state. This field will always be the empty when a Stage is Healthy.
  repeated string issues = 2;

  // ArgoCDApps describes the current state of any related ArgoCD Applications.
  repeated ArgoCDAppStatus argoCDApps = 3;

  // Config is the opaque configuration of all health checks performed on this
  // Stage.
  optional .k8s.io.apiextensions_apiserver.pkg.apis.apiextensions.v1.JSON config = 4;

  // Output is the opaque output of all health checks performed on this Stage.
  optional .k8s.io.apiextensions_apiserver.pkg.apis.apiextensions.v1.JSON output = 5;
}

// HealthCheckStep describes a health check directive which can be executed by
// a Stage to verify the health of a Promotion result.
message HealthCheckStep {
  // Uses identifies a runner that can execute this step.
  //
  // +kubebuilder:validation:MinLength=1
  optional string uses = 1;

  // Config is the configuration for the directive.
  optional .k8s.io.apiextensions_apiserver.pkg.apis.apiextensions.v1.JSON config = 2;
}

// Image describes a specific version of a container image.
message Image {
  // RepoURL describes the repository in which the image can be found.
  optional string repoURL = 1;

  // GitRepoURL specifies the URL of a Git repository that contains the source
  // code for the image repository referenced by the RepoURL field if Kargo was
  // able to infer it.
  optional string gitRepoURL = 2;

  // Tag identifies a specific version of the image in the repository specified
  // by RepoURL.
  optional string tag = 3;

  // Digest identifies a specific version of the image in the repository
  // specified by RepoURL. This is a more precise identifier than Tag.
  optional string digest = 4;
}

// ImageDiscoveryResult represents the result of an image discovery operation
// for an ImageSubscription.
message ImageDiscoveryResult {
  // RepoURL is the repository URL of the image, as specified in the
  // ImageSubscription.
  //
  // +kubebuilder:validation:MinLength=1
  optional string repoURL = 1;

  // Platform is the target platform constraint of the ImageSubscription
  // for which references were discovered. This field is optional, and
  // only populated if the ImageSubscription specifies a Platform.
  optional string platform = 2;

  // References is a list of image references discovered by the Warehouse for
  // the ImageSubscription. An empty list indicates that the discovery
  // operation was successful, but no images matching the ImageSubscription
  // criteria were found.
  //
  // +optional
  repeated DiscoveredImageReference references = 3;
}

// ImageSubscription defines a subscription to an image repository.
message ImageSubscription {
  // RepoURL specifies the URL of the image repository to subscribe to. The
  // value in this field MUST NOT include an image tag. This field is required.
  //
  // +kubebuilder:validation:MinLength=1
  // +kubebuilder:validation:Pattern=`^(\w+([\.-]\w+)*(:[\d]+)?/)?(\w+([\.-]\w+)*)(/\w+([\.-]\w+)*)*$`
  optional string repoURL = 1;

  // GitRepoURL optionally specifies the URL of a Git repository that contains
  // the source code for the image repository referenced by the RepoURL field.
  // When this is specified, Kargo MAY be able to infer and link to the exact
  // revision of that source code that was used to build the image.
  //
  // +kubebuilder:validation:Optional
  // +kubebuilder:validation:Pattern=`^https?://(\w+([\.-]\w+)*@)?\w+([\.-]\w+)*(:[\d]+)?(/.*)?$`
  optional string gitRepoURL = 2;

  // ImageSelectionStrategy specifies the rules for how to identify the newest version
  // of the image specified by the RepoURL field. This field is optional. When
  // left unspecified, the field is implicitly treated as if its value were
  // "SemVer".
  // Accepted values: Digest, Lexical, NewestBuild, SemVer
  //
  // +kubebuilder:default=SemVer
  optional string imageSelectionStrategy = 3;

  // StrictSemvers specifies whether only "strict" semver tags should be
  // considered. A "strict" semver tag is one containing ALL of major, minor,
  // and patch version components. This is enabled by default, but only has any
  // effect when the ImageSelectionStrategy is SemVer. This should be disabled
  // cautiously, as it is not uncommon to tag container images with short Git
  // commit hashes, which have the potential to contain numeric characters only
  // and could be mistaken for a semver string containing the major version
  // number only.
  //
  // +kubebuilder:default=true
  optional bool strictSemvers = 10;

  // SemverConstraint specifies constraints on what new image versions are
  // permissible. The value in this field only has any effect when the
  // ImageSelectionStrategy is SemVer or left unspecified (which is implicitly
  // the same as SemVer). This field is also optional. When left unspecified,
  // (and the ImageSelectionStrategy is SemVer or unspecified), there will be no
  // constraints, which means the latest semantically tagged version of an image
  // will always be used. Care should be taken with leaving this field
  // unspecified, as it can lead to the unanticipated rollout of breaking
  // changes. Refer to Image Updater documentation for more details.
  // More info: https://github.com/masterminds/semver#checking-version-constraints
  //
  // +kubebuilder:validation:Optional
  optional string semverConstraint = 4;

  // AllowTags is a regular expression that can optionally be used to limit the
  // image tags that are considered in determining the newest version of an
  // image. This field is optional.
  //
  // +kubebuilder:validation:Optional
  optional string allowTags = 5;

  // IgnoreTags is a list of tags that must be ignored when determining the
  // newest version of an image. No regular expressions or glob patterns are
  // supported yet. This field is optional.
  //
  // +kubebuilder:validation:Optional
  repeated string ignoreTags = 6;

  // Platform is a string of the form <os>/<arch> that limits the tags that can
  // be considered when searching for new versions of an image. This field is
  // optional. When left unspecified, it is implicitly equivalent to the
  // OS/architecture of the Kargo controller. Care should be taken to set this
  // value correctly in cases where the image referenced by this
  // ImageRepositorySubscription will run on a Kubernetes node with a different
  // OS/architecture than the Kargo controller. At present this is uncommon, but
  // not unheard of.
  //
  // +kubebuilder:validation:Optional
  optional string platform = 7;

  // InsecureSkipTLSVerify specifies whether certificate verification errors
  // should be ignored when connecting to the repository. This should be enabled
  // only with great caution.
  optional bool insecureSkipTLSVerify = 8;

  // DiscoveryLimit is an optional limit on the number of image references
  // that can be discovered for this subscription. The limit is applied after
  // filtering images based on the AllowTags and IgnoreTags fields.
  // When left unspecified, the field is implicitly treated as if its value
  // were "20". The upper limit for this field is 100.
  //
  // +kubebuilder:validation:Minimum=1
  // +kubebuilder:validation:Maximum=100
  // +kubebuilder:default=20
  optional int32 discoveryLimit = 9;
}

// Project is a resource type that reconciles to a specially labeled namespace
// and other TODO: TBD project-level resources.
message Project {
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.ObjectMeta metadata = 1;

  // Spec describes a Project.
  optional ProjectSpec spec = 2;

  // Status describes the Project's current status.
  optional ProjectStatus status = 3;
}

// ProjectList is a list of Project resources.
message ProjectList {
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.ListMeta metadata = 1;

  repeated Project items = 2;
}

// ProjectSpec describes a Project.
message ProjectSpec {
  // PromotionPolicies defines policies governing the promotion of Freight to
  // specific Stages within this Project.
  repeated PromotionPolicy promotionPolicies = 1;
}

// ProjectStatus describes a Project's current status.
message ProjectStatus {
  // Conditions contains the last observations of the Project's current
  // state.
  // +patchMergeKey=type
  // +patchStrategy=merge
  // +listType=map
  // +listMapKey=type
  repeated .k8s.io.apimachinery.pkg.apis.meta.v1.Condition conditions = 3;

  // Phase describes the Project's current phase.
  //
  // Deprecated: Use the Conditions field instead.
  optional string phase = 1;

  // Message is a display message about the Project, including any errors
  // preventing the Project from being reconciled. i.e. If the Phase field has a
  // value of CreationFailed, this field can be expected to explain why.
  //
  // Deprecated: Use the Conditions field instead.
  optional string message = 2;
}

// Promotion represents a request to transition a particular Stage into a
// particular Freight.
message Promotion {
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.ObjectMeta metadata = 1;

  // Spec describes the desired transition of a specific Stage into a specific
  // Freight.
  //
  // +kubebuilder:validation:Required
  optional PromotionSpec spec = 2;

  // Status describes the current state of the transition represented by this
  // Promotion.
  optional PromotionStatus status = 3;
}

// PromotionList contains a list of Promotion
message PromotionList {
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.ListMeta metadata = 1;

  repeated Promotion items = 2;
}

// PromotionPolicy defines policies governing the promotion of Freight to a
// specific Stage.
message PromotionPolicy {
  // +kubebuilder:validation:MinLength=1
  // +kubebuilder:validation:Pattern=^[a-z0-9]([-a-z0-9]*[a-z0-9])?(\.[a-z0-9]([-a-z0-9]*[a-z0-9])?)*$
  optional string stage = 1;

  // AutoPromotionEnabled indicates whether new Freight can automatically be
  // promoted into the Stage referenced by the Stage field. Note: There are may
  // be other conditions also required for an auto-promotion to occur. This
  // field defaults to false, but is commonly set to true for Stages that
  // subscribe to Warehouses instead of other, upstream Stages. This allows
  // users to define Stages that are automatically updated as soon as new
  // artifacts are detected.
  optional bool autoPromotionEnabled = 2;
}

// PromotionReference contains the relevant information about a Promotion
// as observed by a Stage.
message PromotionReference {
  // Name is the name of the Promotion.
  optional string name = 1;

  // Freight is the freight being promoted.
  optional FreightReference freight = 2;

  // Status is the (optional) status of the Promotion.
  optional PromotionStatus status = 3;

  // FinishedAt is the time at which the Promotion was completed.
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.Time finishedAt = 4;
}

// PromotionSpec describes the desired transition of a specific Stage into a
// specific Freight.
message PromotionSpec {
  // Stage specifies the name of the Stage to which this Promotion
  // applies. The Stage referenced by this field MUST be in the same
  // namespace as the Promotion.
  //
  // +kubebuilder:validation:MinLength=1
  // +kubebuilder:validation:Pattern=^[a-z0-9]([-a-z0-9]*[a-z0-9])?(\.[a-z0-9]([-a-z0-9]*[a-z0-9])?)*$
  optional string stage = 1;

  // Freight specifies the piece of Freight to be promoted into the Stage
  // referenced by the Stage field.
  //
  // +kubebuilder:validation:MinLength=1
  optional string freight = 2;

  // Vars is a list of variables that can be referenced by expressions in
  // promotion steps.
  repeated PromotionVariable vars = 4;

  // Steps specifies the directives to be executed as part of this Promotion.
  // The order in which the directives are executed is the order in which they
  // are listed in this field.
  repeated PromotionStep steps = 3;
}

// PromotionStatus describes the current state of the transition represented by
// a Promotion.
message PromotionStatus {
  // LastHandledRefresh holds the value of the most recent AnnotationKeyRefresh
  // annotation that was handled by the controller. This field can be used to
  // determine whether the request to refresh the resource has been handled.
  // +optional
  optional string lastHandledRefresh = 4;

  // Phase describes where the Promotion currently is in its lifecycle.
  optional string phase = 1;

  // Message is a display message about the promotion, including any errors
  // preventing the Promotion controller from executing this Promotion.
  // i.e. If the Phase field has a value of Failed, this field can be expected
  // to explain why.
  optional string message = 2;

  // Freight is the detail of the piece of freight that was referenced by this promotion.
  optional FreightReference freight = 5;

  // FreightCollection contains the details of the piece of Freight referenced
  // by this Promotion as well as any additional Freight that is carried over
  // from the target Stage's current state.
  optional FreightCollection freightCollection = 7;

  // HealthChecks contains the health check directives to be executed after
  // the Promotion has completed.
  repeated HealthCheckStep healthChecks = 8;

  // FinishedAt is the time when the promotion was completed.
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.Time finishedAt = 6;

  // CurrentStep is the index of the current promotion step being executed. This
  // permits steps that have already run successfully to be skipped on
  // subsequent reconciliations attempts.
  optional int64 currentStep = 9;

  // CurrentStepAttempt is the number of times the current step has been
  // attempted.
  optional int64 currentStepAttempt = 11;

  // State stores the state of the promotion process between reconciliation
  // attempts.
  optional .k8s.io.apiextensions_apiserver.pkg.apis.apiextensions.v1.JSON state = 10;
}

// PromotionStep describes a directive to be executed as part of a Promotion.
message PromotionStep {
  // Uses identifies a runner that can execute this step.
  //
  // +kubebuilder:validation:MinLength=1
  optional string uses = 1;

  // As is the alias this step can be referred to as.
  optional string as = 2;

  // Retry is the retry policy for this step.
  optional PromotionStepRetry retry = 4;

  // Config is opaque configuration for the PromotionStep that is understood
  // only by each PromotionStep's implementation. It is legal to utilize
  // expressions in defining values at any level of this block.
  // See https://docs.kargo.io/references/expression-language for details.
  optional .k8s.io.apiextensions_apiserver.pkg.apis.apiextensions.v1.JSON config = 3;
}

// PromotionStepRetry describes the retry policy for a PromotionStep.
message PromotionStepRetry {
  // Attempts is the number of times the step can be attempted before the
  // PromotionStep is marked as failed.
  //
  // If this field is set to 1, the step will not be retried. If this
  // field is set to -1, the step will be retried indefinitely.
  //
  // The default of this field depends on the step being executed. Refer to
  // the documentation for the specific step for more information.
  optional int64 attempts = 1;
}

// PromotionTemplate defines a template for a Promotion that can be used to
// incorporate Freight into a Stage.
message PromotionTemplate {
  optional PromotionTemplateSpec spec = 1;
}

// PromotionTemplateSpec describes the (partial) specification of a Promotion
// for a Stage. This is a template that can be used to create a Promotion for a
// Stage.
message PromotionTemplateSpec {
  // Vars is a list of variables that can be referenced by expressions in
  // promotion steps.
  repeated PromotionVariable vars = 2;

  // Steps specifies the directives to be executed as part of a Promotion.
  // The order in which the directives are executed is the order in which they
  // are listed in this field.
  //
  // +kubebuilder:validation:MinItems=1
  repeated PromotionStep steps = 1;
}

// PromotionVariable describes a single variable that may be referenced by
// expressions in promotion steps.
message PromotionVariable {
  // Name is the name of the variable.
  //
  // +kubebuilder:validation:MinLength=1
  // +kubebuilder:validation:Pattern=^[a-zA-Z_]\w*$
  optional string name = 1;

  // Value is the value of the variable. It is allowed to utilize expressions
  // in the value.
  // See https://docs.kargo.io/references/expression-language for details.
  optional string value = 2;
}

// RepoSubscription describes a subscription to ONE OF a Git repository, a
// container image repository, or a Helm chart repository.
message RepoSubscription {
  // Git describes a subscriptions to a Git repository.
  optional GitSubscription git = 1;

  // Image describes a subscription to container image repository.
  optional ImageSubscription image = 2;

  // Chart describes a subscription to a Helm chart repository.
  optional ChartSubscription chart = 3;
}

// Stage is the Kargo API's main type.
message Stage {
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.ObjectMeta metadata = 1;

  // Spec describes sources of Freight used by the Stage and how to incorporate
  // Freight into the Stage.
  //
  // +kubebuilder:validation:Required
  optional StageSpec spec = 2;

  // Status describes the Stage's current and recent Freight, health, and more.
  optional StageStatus status = 3;
}

// StageList is a list of Stage resources.
message StageList {
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.ListMeta metadata = 1;

  repeated Stage items = 2;
}

// StageSpec describes the sources of Freight used by a Stage and how to
// incorporate Freight into the Stage.
message StageSpec {
  // Shard is the name of the shard that this Stage belongs to. This is an
  // optional field. If not specified, the Stage will belong to the default
  // shard. A defaulting webhook will sync the value of the
  // kargo.akuity.io/shard label with the value of this field. When this field
  // is empty, the webhook will ensure that label is absent.
  optional string shard = 4;

  // RequestedFreight expresses the Stage's need for certain pieces of Freight,
  // each having originated from a particular Warehouse. This list must be
  // non-empty. In the common case, a Stage will request Freight having
  // originated from just one specific Warehouse. In advanced cases, requesting
  // Freight from multiple Warehouses provides a method of advancing new
  // artifacts of different types through parallel pipelines at different
  // speeds. This can be useful, for instance, if a Stage is home to multiple
  // microservices that are independently versioned.
  //
  // +kubebuilder:validation:MinItems=1
  repeated FreightRequest requestedFreight = 5;

  // PromotionTemplate describes how to incorporate Freight into the Stage
  // using a Promotion.
  optional PromotionTemplate promotionTemplate = 6;

  // Verification describes how to verify a Stage's current Freight is fit for
  // promotion downstream.
  optional Verification verification = 3;
}

// StageStatus describes a Stages's current and recent Freight, health, and
// more.
message StageStatus {
  // Conditions contains the last observations of the Stage's current
  // state.
  // +patchMergeKey=type
  // +patchStrategy=merge
  // +listType=map
  // +listMapKey=type
  repeated .k8s.io.apimachinery.pkg.apis.meta.v1.Condition conditions = 13;

  // LastHandledRefresh holds the value of the most recent AnnotationKeyRefresh
  // annotation that was handled by the controller. This field can be used to
  // determine whether the request to refresh the resource has been handled.
  // +optional
  optional string lastHandledRefresh = 11;

  // Phase describes where the Stage currently is in its lifecycle.
  optional string phase = 1;

  // FreightHistory is a list of recent Freight selections that were deployed
  // to the Stage. By default, the last ten Freight selections are stored.
  // The first item in the list is the most recent Freight selection and
  // currently deployed to the Stage, subsequent items are older selections.
  repeated FreightCollection freightHistory = 4;

  // FreightSummary is human-readable text maintained by the controller that
  // summarizes what Freight is currently deployed to the Stage. For Stages that
  // request a single piece of Freight AND the request has been fulfilled, this
  // field will simply contain the name of the Freight. For Stages that request
  // a single piece of Freight AND the request has NOT been fulfilled, or for
  // Stages that request multiple pieces of Freight, this field will contain a
  // summary of fulfilled/requested Freight. The existence of this field is a
  // workaround for kubectl limitations so that this complex but valuable
  // information can be displayed in a column in response to `kubectl get
  // stages`.
  optional string freightSummary = 12;

  // Health is the Stage's last observed health.
  optional Health health = 8;

  // Message describes any errors that are preventing the Stage controller
  // from assessing Stage health or from finding new Freight.
  optional string message = 9;

  // ObservedGeneration represents the .metadata.generation that this Stage
  // status was reconciled against.
  optional int64 observedGeneration = 6;

  // CurrentPromotion is a reference to the currently Running promotion.
  optional PromotionReference currentPromotion = 7;

  // LastPromotion is a reference to the last completed promotion.
  optional PromotionReference lastPromotion = 10;
}

// Verification describes how to verify that a Promotion has been successful
// using Argo Rollouts AnalysisTemplates.
message Verification {
  // AnalysisTemplates is a list of AnalysisTemplates from which AnalysisRuns
  // should be created to verify a Stage's current Freight is fit to be promoted
  // downstream.
  repeated AnalysisTemplateReference analysisTemplates = 1;

  // AnalysisRunMetadata contains optional metadata that should be applied to
  // all AnalysisRuns.
  optional AnalysisRunMetadata analysisRunMetadata = 2;

  // Args lists arguments that should be added to all AnalysisRuns.
  repeated AnalysisRunArgument args = 3;
}

// VerificationInfo contains the details of an instance of a Verification
// process.
message VerificationInfo {
  // ID is the identifier of the Verification process.
  optional string id = 4;

  // Actor is the name of the entity that initiated or aborted the
  // Verification process.
  optional string actor = 7;

  // StartTime is the time at which the Verification process was started.
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.Time startTime = 5;

  // Phase describes the current phase of the Verification process. Generally,
  // this will be a reflection of the underlying AnalysisRun's phase, however,
  // there are exceptions to this, such as in the case where an AnalysisRun
  // cannot be launched successfully.
  optional string phase = 1;

  // Message may contain additional information about why the verification
  // process is in its current phase.
  optional string message = 2;

  // AnalysisRun is a reference to the Argo Rollouts AnalysisRun that implements
  // the Verification process.
  optional AnalysisRunReference analysisRun = 3;

  // FinishTime is the time at which the Verification process finished.
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.Time finishTime = 6;
}

// VerifiedStage describes a Stage in which Freight has been verified.
message VerifiedStage {
}

// Warehouse is a source of Freight.
message Warehouse {
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.ObjectMeta metadata = 1;

  // Spec describes sources of artifacts.
  //
  // +kubebuilder:validation:Required
  optional WarehouseSpec spec = 2;

  // Status describes the Warehouse's most recently observed state.
  optional WarehouseStatus status = 3;
}

// WarehouseList is a list of Warehouse resources.
message WarehouseList {
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.ListMeta metadata = 1;

  repeated Warehouse items = 2;
}

// WarehouseSpec describes sources of versioned artifacts to be included in
// Freight produced by this Warehouse.
message WarehouseSpec {
  // Shard is the name of the shard that this Warehouse belongs to. This is an
  // optional field. If not specified, the Warehouse will belong to the default
  // shard. A defaulting webhook will sync this field with the value of the
  // kargo.akuity.io/shard label. When the shard label is not present or differs
  // from the value of this field, the defaulting webhook will set the label to
  // the value of this field. If the shard label is present and this field is
  // empty, the defaulting webhook will set the value of this field to the value
  // of the shard label.
  optional string shard = 2;

  // Interval is the reconciliation interval for this Warehouse. On each
  // reconciliation, the Warehouse will discover new artifacts and optionally
  // produce new Freight. This field is optional. When left unspecified, the
  // field is implicitly treated as if its value were "5m0s".
  //
  // +kubebuilder:validation:Type=string
  // +kubebuilder:validation:Pattern="^([0-9]+(\\.[0-9]+)?(s|m|h))+$"
  // +kubebuilder:default="5m0s"
  optional .k8s.io.apimachinery.pkg.apis.meta.v1.Duration interval = 4;

  // FreightCreationPolicy describes how Freight is created by this Warehouse.
  // This field is optional. When left unspecified, the field is implicitly
  // treated as if its value were "Automatic".
  // Accepted values: Automatic, Manual
  //
  // +kubebuilder:default=Automatic
  // +kubebuilder:validation:Optional
  optional string freightCreationPolicy = 3;

  // Subscriptions describes sources of artifacts to be included in Freight
  // produced by this Warehouse.
  //
  // +kubebuilder:validation:MinItems=1
  repeated RepoSubscription subscriptions = 1;
}

// WarehouseStatus describes a Warehouse's most recently observed state.
message WarehouseStatus {
  // Conditions contains the last observations of the Warehouse's current
  // state.
  // +patchMergeKey=type
  // +patchStrategy=merge
  // +listType=map
  // +listMapKey=type
  repeated .k8s.io.apimachinery.pkg.apis.meta.v1.Condition conditions = 9;

  // LastHandledRefresh holds the value of the most recent AnnotationKeyRefresh
  // annotation that was handled by the controller. This field can be used to
  // determine whether the request to refresh the resource has been handled.
  // +optional
  optional string lastHandledRefresh = 6;

  // ObservedGeneration represents the .metadata.generation that this Warehouse
  // was reconciled against.
  optional int64 observedGeneration = 4;

  // LastFreightID is a reference to the system-assigned identifier (name) of
  // the most recent Freight produced by the Warehouse.
  optional string lastFreightID = 8;

  // DiscoveredArtifacts holds the artifacts discovered by the Warehouse.
  optional DiscoveredArtifacts discoveredArtifacts = 7;
}

