// Code generated by sidekick. DO NOT EDIT.
//
// Copyright 2026 Google LLC
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     https://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

import Foundation
import GoogleCloudWkt

/// A widget showing the latest value of a metric, and how this value relates to
/// one or more thresholds.
public struct Scorecard: Codable, Equatable, GoogleCloudWkt._AnyPackable,
  Sendable
{
  /// Required. Fields for querying time series data from the
  /// Stackdriver metrics API.
  public var timeSeriesQuery: TimeSeriesQuery? = nil

  /// The thresholds used to determine the state of the scorecard given the
  /// time series' current value. For an actual value x, the scorecard is in a
  /// danger state if x is less than or equal to a danger threshold that triggers
  /// below, or greater than or equal to a danger threshold that triggers above.
  /// Similarly, if x is above/below a warning threshold that triggers
  /// above/below, then the scorecard is in a warning state - unless x also puts
  /// it in a danger state. (Danger trumps warning.)
  ///
  /// As an example, consider a scorecard with the following four thresholds:
  ///
  /// ```
  /// {
  ///   value: 90,
  ///   category: 'DANGER',
  ///   trigger: 'ABOVE',
  /// },
  /// {
  ///   value: 70,
  ///   category: 'WARNING',
  ///   trigger: 'ABOVE',
  /// },
  /// {
  ///   value: 10,
  ///   category: 'DANGER',
  ///   trigger: 'BELOW',
  /// },
  /// {
  ///   value: 20,
  ///   category: 'WARNING',
  ///   trigger: 'BELOW',
  /// }
  /// ```
  ///
  /// Then: values less than or equal to 10 would put the scorecard in a DANGER
  /// state, values greater than 10 but less than or equal to 20 a WARNING state,
  /// values strictly between 20 and 70 an OK state, values greater than or equal
  /// to 70 but less than 90 a WARNING state, and values greater than or equal to
  /// 90 a DANGER state.
  public var thresholds: [Threshold] = []

  /// Defines the optional additional chart shown on the scorecard. If
  /// neither is included - then a default scorecard is shown.
  public var dataView: OneOf_DataView? = nil

  /// Initialize a new instance of `Scorecard`.
  public init() {}

  /// Use `config` to return a new instance of this object, with some fields updated.
  ///
  /// Commonly used to initialize the value, for example:
  ///
  /// ```
  /// let value = Scorecard().with { $0.timeSeriesQuery = ... }
  /// ```
  public func with(_ config: (inout Self) throws -> Swift.Void) rethrows -> Self {
    var copy = self
    try config(&copy)
    return copy
  }

  private enum CodingKeys: Swift.String, CodingKey {
    case timeSeriesQuery = "timeSeriesQuery"
    case gaugeView = "gaugeView"
    case sparkChartView = "sparkChartView"
    case blankView = "blankView"
    case thresholds = "thresholds"
  }

  public init(from decoder: Decoder) throws {
    let container = try decoder.container(keyedBy: CodingKeys.self)
    self.timeSeriesQuery = try container.decodeIfPresent(
      TimeSeriesQuery.self, forKey: .timeSeriesQuery)
    self.thresholds = try container.decode([Threshold].self, forKey: .thresholds)

    var dataView: OneOf_DataView? = nil
    let dataViewCheckAndSet = {
      if dataView != nil {
        throw DecodingError.dataCorrupted(
          DecodingError.Context(
            codingPath: decoder.codingPath,
            debugDescription: "Multiple values set for oneof 'dataView'"))
      }
      dataView = $0
    }
    if let gaugeView = try container.decodeIfPresent(Scorecard.GaugeView?.self, forKey: .gaugeView)
    {
      try dataViewCheckAndSet(.gaugeView(gaugeView))
    }
    if let sparkChartView = try container.decodeIfPresent(
      Scorecard.SparkChartView?.self, forKey: .sparkChartView)
    {
      try dataViewCheckAndSet(.sparkChartView(sparkChartView))
    }
    if let blankView = try container.decodeIfPresent(GoogleCloudWkt.Empty?.self, forKey: .blankView)
    {
      try dataViewCheckAndSet(.blankView(blankView))
    }
    self.dataView = dataView
  }

  public func encode(to encoder: Encoder) throws {
    var container = encoder.container(keyedBy: CodingKeys.self)
    try container.encode(self.timeSeriesQuery, forKey: .timeSeriesQuery)
    try container.encode(self.thresholds, forKey: .thresholds)

    if let choice = self.dataView {
      switch choice {
      case .gaugeView(let value):
        try container.encode(value, forKey: .gaugeView)
      case .sparkChartView(let value):
        try container.encode(value, forKey: .sparkChartView)
      case .blankView(let value):
        try container.encode(value, forKey: .blankView)
      }
    }
  }

  /// A gauge chart shows where the current value sits within a pre-defined
  /// range. The upper and lower bounds should define the possible range of
  /// values for the scorecard's query (inclusive).
  public struct GaugeView: Codable, Equatable, GoogleCloudWkt._AnyPackable,
    Sendable
  {
    /// The lower bound for this gauge chart. The value of the chart should
    /// always be greater than or equal to this.
    public var lowerBound: Swift.Double = Swift.Double()

    /// The upper bound for this gauge chart. The value of the chart should
    /// always be less than or equal to this.
    public var upperBound: Swift.Double = Swift.Double()

    /// Initialize a new instance of `GaugeView`.
    public init() {}

    /// Use `config` to return a new instance of this object, with some fields updated.
    ///
    /// Commonly used to initialize the value, for example:
    ///
    /// ```
    /// let value = GaugeView().with { $0.lowerBound = ... }
    /// ```
    public func with(_ config: (inout Self) throws -> Swift.Void) rethrows -> Self {
      var copy = self
      try config(&copy)
      return copy
    }

    public static var _anyTypeUrl: Swift.String {
      return "type.googleapis.com/google.monitoring.dashboard.v1.Scorecard.GaugeView"
    }
    public init(fromAny any: GoogleCloudWkt.`Any`) throws {
      self = try GoogleCloudWkt._slowAnyDeserialize(Self.self, from: any)
    }
    public func _pack() throws -> GoogleCloudWkt.Struct {
      return try GoogleCloudWkt._slowAnySerialize(message: self)
    }
  }

  /// A sparkChart is a small chart suitable for inclusion in a table-cell or
  /// inline in text. This message contains the configuration for a sparkChart
  /// to show up on a Scorecard, showing recent trends of the scorecard's
  /// timeseries.
  public struct SparkChartView: Codable, Equatable, GoogleCloudWkt._AnyPackable,
    Sendable
  {
    /// Required. The type of sparkchart to show in this chartView.
    public var sparkChartType: SparkChartType = SparkChartType()

    /// The lower bound on data point frequency in the chart implemented by
    /// specifying the minimum alignment period to use in a time series query.
    /// For example, if the data is published once every 10 minutes it would not
    /// make sense to fetch and align data at one minute intervals. This field is
    /// optional and exists only as a hint.
    public var minAlignmentPeriod: GoogleCloudWkt.Duration? = nil

    /// Initialize a new instance of `SparkChartView`.
    public init() {}

    /// Use `config` to return a new instance of this object, with some fields updated.
    ///
    /// Commonly used to initialize the value, for example:
    ///
    /// ```
    /// let value = SparkChartView().with { $0.sparkChartType = ... }
    /// ```
    public func with(_ config: (inout Self) throws -> Swift.Void) rethrows -> Self {
      var copy = self
      try config(&copy)
      return copy
    }

    public static var _anyTypeUrl: Swift.String {
      return "type.googleapis.com/google.monitoring.dashboard.v1.Scorecard.SparkChartView"
    }
    public init(fromAny any: GoogleCloudWkt.`Any`) throws {
      self = try GoogleCloudWkt._slowAnyDeserialize(Self.self, from: any)
    }
    public func _pack() throws -> GoogleCloudWkt.Struct {
      return try GoogleCloudWkt._slowAnySerialize(message: self)
    }
  }

  /// Defines the optional additional chart shown on the scorecard. If
  /// neither is included - then a default scorecard is shown.
  public enum OneOf_DataView: Codable, Equatable, Sendable {
    /// Will cause the scorecard to show a gauge chart.
    indirect case gaugeView(Scorecard.GaugeView?)
    /// Will cause the scorecard to show a spark chart.
    indirect case sparkChartView(Scorecard.SparkChartView?)
    /// Will cause the `Scorecard` to show only the value, with no indicator to
    /// its value relative to its thresholds.
    indirect case blankView(GoogleCloudWkt.Empty?)
  }

  public static var _anyTypeUrl: Swift.String {
    return "type.googleapis.com/google.monitoring.dashboard.v1.Scorecard"
  }
  public init(fromAny any: GoogleCloudWkt.`Any`) throws {
    self = try GoogleCloudWkt._slowAnyDeserialize(Self.self, from: any)
  }
  public func _pack() throws -> GoogleCloudWkt.Struct {
    return try GoogleCloudWkt._slowAnySerialize(message: self)
  }
}
