// 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 "formats/format.h"

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

#include "absl/status/status.h"
#include "absl/status/status_matchers.h"
#include "absl/status/statusor.h"
#include "absl/strings/string_view.h"
#include "formats/assessor.h"
#include "formats/asset_box.h"
#include "formats/byte_range.h"
#include "formats/extractor.h"
#include "gmock/gmock.h"
#include "gtest/gtest.h"
#include "riegeli/bytes/reader.h"

namespace credentio {
namespace {

using ::absl_testing::IsOk;
using ::absl_testing::StatusIs;
using ::testing::HasSubstr;

class FakeAssessor : public FormatAssessor {
 public:
  FakeAssessor() = default;
  ~FakeAssessor() override = default;

  absl::StatusOr<bool> IsSupported(riegeli::Reader& input) const override {
    return absl::UnimplementedError("Not implemented");
  }
};

class FakeExtractor : public FormatExtractor {
 public:
  FakeExtractor() = default;
  ~FakeExtractor() override = default;

  absl::StatusOr<std::string> ExtractManifestStore(
      riegeli::Reader& input) const override {
    return absl::UnimplementedError("Not implemented");
  }

  absl::StatusOr<std::optional<ByteRange>> ExtractManifestStoreLocation(
      riegeli::Reader& input, ExtractOptions options) const override {
    return absl::UnimplementedError("Not implemented");
  }

  absl::StatusOr<std::vector<AssetBox>> ExtractBoxes(
      riegeli::Reader& input, ExtractOptions options) const override {
    return absl::UnimplementedError("Not implemented");
  }

  bool MightBeC2paManifestStore(absl::string_view payload) const override {
    return true;
  }
};

TEST(FormatTest, FailsIfNoAssessor) {
  EXPECT_THAT(Format::Create(FormatOptions{
                  .extractor = std::make_unique<FakeExtractor>(),
                  .mime_types = {"jpeg"},
              }),
              StatusIs(absl::StatusCode::kInvalidArgument,
                       HasSubstr("FormatAssessor is required")));
}

TEST(FormatTest, FailsIfNoExtractor) {
  EXPECT_THAT(Format::Create(FormatOptions{
                  .assessor = std::make_unique<FakeAssessor>(),
                  .mime_types = {"jpeg"},
              }),
              StatusIs(absl::StatusCode::kInvalidArgument,
                       HasSubstr("FormatExtractor is required")));
}

TEST(FormatTest, FailsIfNoMimeTypes) {
  EXPECT_THAT(Format::Create(FormatOptions{
                  .assessor = std::make_unique<FakeAssessor>(),
                  .extractor = std::make_unique<FakeExtractor>(),
              }),
              StatusIs(absl::StatusCode::kInvalidArgument,
                       HasSubstr("At least one mime type is required")));
}

TEST(FormatTest, Succeeds) {
  EXPECT_THAT(Format::Create(FormatOptions{
                  .assessor = std::make_unique<FakeAssessor>(),
                  .extractor = std::make_unique<FakeExtractor>(),
                  .mime_types = {"jpeg"},
              }),
              IsOk());
}

}  // namespace
}  // namespace credentio
