// 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.
//

#ifndef THIRD_PARTY_CREDENTIO_VALIDATOR_GRAPH_H_
#define THIRD_PARTY_CREDENTIO_VALIDATOR_GRAPH_H_

#include <memory>
#include <optional>
#include <stack>
#include <string>
#include <vector>

#include "absl/base/nullability.h"
#include "absl/container/flat_hash_map.h"
#include "absl/container/flat_hash_set.h"
#include "absl/log/die_if_null.h"
#include "absl/status/status.h"
#include "absl/status/statusor.h"
#include "absl/strings/string_view.h"
#include "assertion/validator.h"
#include "claim/validator.h"
#include "crypto/hash.h"
#include "jumbf/box.h"
#include "jumbf/uri.h"
#include "proto/assertion.pb.h"
#include "proto/manifest.pb.h"
#include "proto/validation_result.pb.h"
#include "proto/validation_status.pb.h"
#include "validator/tracker.h"
#include "validator/validator_options.h"

namespace credentio {

class ManifestGraph {
 public:
  ManifestGraph(const jumbf::SuperBox* absl_nonnull active_manifest,
                const jumbf::UriResolver* absl_nonnull uri_resolver,
                const AssertionValidator* absl_nonnull assertion_validator,
                const ClaimValidator* absl_nonnull claim_validator,
                const HashCheckerFactory* absl_nonnull hash_checker_factory,
                const ValidatorOptions* absl_nonnull options)
      : active_manifest_(*ABSL_DIE_IF_NULL(active_manifest)),
        uri_resolver_(*ABSL_DIE_IF_NULL(uri_resolver)),
        assertion_validator_(*ABSL_DIE_IF_NULL(assertion_validator)),
        claim_validator_(*ABSL_DIE_IF_NULL(claim_validator)),
        hash_checker_factory_(*ABSL_DIE_IF_NULL(hash_checker_factory)),
        options_(*ABSL_DIE_IF_NULL(options)) {}

  // Perform claim and assertion validation for the active manifest and all
  // ingredient manifests reachable from the active manifest. Caller should
  // follow with calling the `Validate` method from
  // of bindings/validator.h to validate
  // content bindings.
  absl::StatusOr<std::unique_ptr<PartialValidationResultProto>> Validate();

 private:
  // Internal validation state of a manifest, tracking whether the manifest has
  // been processed by `ValidateInternal` yet.
  enum class InternalValidationState {
    // `ValidateInternal` has not processed the manifest yet.
    kUnvalidated,
    // `ValidateInternal` is currently processing the manifest.
    kBeingValidated,
    // `ValidateInternal` has processed the manifest already.
    kValidated,
  };

  struct IngredientAssertion {
    const Assertion* assertion = nullptr;
    std::string assertion_uri;
  };

  // State associated with a specific manifest during validation.
  struct ManifestState {
    InternalValidationState validation_state =
        InternalValidationState::kUnvalidated;
    // Absolute paths of all assertions in this manifest that have been reported
    // (in another manifest) as redacted.
    absl::flat_hash_set<std::string> redacted_assertions;
    // Ingredient assertions that reference this manifest.
    std::vector<IngredientAssertion> referencing_ingredient_assertions;

    // Validation result, complete if `validation_state` is kValidated.
    Manifest manifest;
  };

  // Returns the manifest state for the given path, creating it if it does not
  // exist.
  ManifestState& GetOrCreateManifestState(absl::string_view path);
  // Returns the manifest state for the given path, or an error if the manifest
  // is not yet validated.
  absl::StatusOr<ManifestState* absl_nonnull> GetValidatedManifestState(
      absl::string_view path);

  // Performs the first pass of the ingredient validation algorithm in
  // https://spec.c2pa.org/specifications/specifications/2.4/specs/C2PA_Specification.html#_performing_explicit_validation
  // for the active manifest to populate the set of redacted assertions and the
  // set of ingredient manifests and to perform claim and (non-redacted)
  // assertion validation for all manifests in the graph.
  absl::Status ValidateGraph();
  absl::Status ValidateNode(const jumbf::SuperBox& node,
                            bool is_active_manifest,
                            std::stack<const jumbf::SuperBox*>& to_visit);

  // This method performs the second pass of the ingredient validation algorithm
  // in
  // https://spec.c2pa.org/specifications/specifications/2.4/specs/C2PA_Specification.html#_performing_explicit_validation.
  // In this pass, we perform the hash validation checks for all ingredient
  // manifests reachable from the active manifest, using claim signature or
  // manifest hash validation methods. We also process the `validationResults`
  // sections of v3 ingredient assertions and update the
  // `PartialValidationResultProto` accordingly.
  absl::StatusOr<std::unique_ptr<PartialValidationResultProto>>
  ValidateWithRedactions(std::unique_ptr<PartialValidationResultProto> result);

  // Records the given redaction in the `redacted_assertions_` map.
  void ProcessRedaction(absl::string_view redacted_assertion_uri,
                        absl::string_view manifest_path,
                        ValidationTracker& tracker);

  // Processes the given ingredient assertion, returning the absolute path to
  // the ingredient's manifest if it should be processed.
  std::optional<std::string> ProcessIngredientAssertion(
      const Assertion& assertion, absl::string_view manifest_path,
      absl::string_view default_algorithm, ValidationTracker& tracker);

  // Performs post-processing to complete population of the validation result
  // following graph traversal via ValidateNode.
  absl::StatusOr<std::unique_ptr<PartialValidationResultProto>>
  ValidatePostProcess();

  // RAII-style lock to manage validation state transitions using local scope.
  class InternalValidationStateLock {
   public:
    explicit InternalValidationStateLock(
        ManifestState* absl_nonnull manifest_state);

    ~InternalValidationStateLock();

   private:
    ManifestState& manifest_state_;
  };

  const jumbf::SuperBox& active_manifest_;
  const jumbf::UriResolver& uri_resolver_;
  const AssertionValidator& assertion_validator_;
  const ClaimValidator& claim_validator_;
  const HashCheckerFactory& hash_checker_factory_;
  const ValidatorOptions& options_;
  // Manifest validation states, keyed by manifest path.
  absl::flat_hash_map<std::string, std::unique_ptr<ManifestState>> manifests_;
  // Ingredient manifest paths, in pre-order traversal ordering.
  std::vector<std::string> ingredient_manifest_paths_;
  std::string manifest_with_content_bindings_label_;
};

}  // namespace credentio

#endif  // THIRD_PARTY_CREDENTIO_VALIDATOR_GRAPH_H_
