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

#include "bindings/bmff_binding_hasher.h"

#include <optional>
#include <string>

#include "absl/status/status.h"
#include "absl/status/status_matchers.h"
#include "bindings/binding_hasher.h"
#include "formats/bmff/test_utils.h"
#include "gmock/gmock.h"
#include "gtest/gtest.h"
#include "proto/bmff_based_hash_assertion.pb.h"
#include "proto/manifest.pb.h"
#include "riegeli/bytes/string_reader.h"

namespace credentio {
namespace {

using ::absl_testing::IsOk;
using ::absl_testing::StatusIs;
using ::testing::Eq;
using ::testing::Ne;

TEST(BmffBindingHasherTest, DigestInvalidInput) {
  riegeli::StringReader<> input("some fake content");
  BmffBasedHashAssertion assertion;
  StatusBindingHasherTracker tracker;
  BmffBindingHasher hasher(&assertion, &tracker);
  EXPECT_THAT(hasher.Digest(input), Eq(std::nullopt));
  EXPECT_THAT(tracker.status(), StatusIs(absl::StatusCode::kDataLoss));
}

TEST(BmffBindingHasherTest, XPathBypassWithBracketBoxType) {
  std::string contents1 = credentio_testing::Box("[moo", "payload1_data_here");
  std::string contents2 = credentio_testing::Box("[moo", "payload2_data_here");
  riegeli::StringReader<> input1(contents1);
  riegeli::StringReader<> input2(contents2);

  BmffBasedHashAssertion assertion;
  assertion.set_alg("sha256");
  auto* exclusion = assertion.add_exclusions();
  exclusion->set_xpath("/moov");

  StatusBindingHasherTracker tracker1;
  BmffBindingHasher hasher1(&assertion, &tracker1);
  auto digest1 = hasher1.Digest(input1);
  ASSERT_TRUE(digest1.has_value());
  EXPECT_THAT(tracker1.status(), IsOk());

  StatusBindingHasherTracker tracker2;
  BmffBindingHasher hasher2(&assertion, &tracker2);
  auto digest2 = hasher2.Digest(input2);
  ASSERT_TRUE(digest2.has_value());
  EXPECT_THAT(tracker2.status(), IsOk());

  // Without the fix, "[moo" was treated as matching "/moov", causing the entire
  // box payload to be excluded and making digest1 == digest2.
  // With the fix, the box is not excluded, so different payloads produce
  // different digests.
  EXPECT_THAT(digest1, Ne(digest2));
}

}  // namespace
}  // namespace credentio
