blob: 3aaa90080f7294049a90ca2bc3226ebf854facd1 [file]
// Protocol Buffers - Google's data interchange format
// Copyright 2026 Google LLC. All rights reserved.
//
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file or at
// https://developers.google.com/open-source/licenses/bsd
#ifndef GOOGLE_PROTOBUF_CONFORMANCE_FAILURE_LIST_H__
#define GOOGLE_PROTOBUF_CONFORMANCE_FAILURE_LIST_H__
#include <string>
#include "absl/container/flat_hash_map.h"
#include "absl/status/status.h"
#include "absl/strings/string_view.h"
#include "absl/types/optional.h"
#include "conformance/failure_list_trie_node.h"
#include "conformance/testee.h"
namespace google {
namespace protobuf {
namespace conformance {
namespace internal {
// The form a failure message takes in a failure list: surrounding whitespace
// and newlines removed, truncated to 128 characters. Expected messages are
// normalized when they are added and actual ones when they are judged, so
// that FailureList::VerdictOnFailure() compares like with like.
std::string FormatFailureMessage(absl::string_view message);
// The expected failures of a conformance run, as the failure list files list
// them, plus the enforcement level: everything needed to judge one test's
// outcome, and nothing that changes once the tests run. The ResultLedger
// (result_ledger.h) builds it while loading the failure lists and tallies the
// outcomes against it. Yields() (matchers.h) asks the run's list, through
// the global ledger (see global_test_environment.h), for its verdicts.
class FailureList {
public:
FailureList() : entries_("root") {}
// The lowest priority whose failures fail the suite (see TestPriority in
// testee.h). VerdictOnFailure() tolerates a failing test of a lower priority
// unless it is listed. Defaults to kLowestPriority, which enforces every
// priority.
void set_enforcement_level(TestPriority level) { enforcement_level_ = level; }
TestPriority enforcement_level() const { return enforcement_level_; }
// Adds the entry `test_name`, a test name or a wildcard, as expected to fail
// with `failure_message` (see VerdictOnFailure()). Returns an error if the
// entry is already present or contains an invalid wildcard.
absl::Status Add(absl::string_view test_name,
absl::string_view failure_message);
// The verdict on a test that succeeded: an error naming the entry it
// matched if the test was expected to fail.
absl::Status VerdictOnSuccess(absl::string_view test_name) const;
// The verdict on a test that failed with `failure_message`. OK if the
// failure doesn't fail the suite. That is the case when the test is in the
// failure list with a matching message (an expected failure), or when it
// isn't listed and `priority` is above the enforcement level (a tolerated
// failure). Otherwise the failure is unexpected and the error says why. A
// listed test is checked whatever its priority, so that the failure list
// can't go stale unnoticed. The normalized actual message only needs to
// start with the expected message, so an empty expected message matches any
// failure.
absl::Status VerdictOnFailure(absl::string_view test_name,
TestPriority priority,
absl::string_view failure_message) const;
// The verdict on a test the testee skipped for `skip_reason`: an error
// naming the entry it matched if the test is in the failure list, since a
// skipped test can't be an expected failure. Whether that error fails the
// test is the caller's policy; Yields() fails such a test.
absl::Status VerdictOnSkip(absl::string_view test_name,
absl::string_view skip_reason) const;
// The failure list entry `test_name` matches, possibly a wildcard, if any.
absl::optional<std::string> MatchingEntry(absl::string_view test_name) const;
// The expected failure message of the entry `entry`, normalized (see
// FormatFailureMessage()). `entry` is an entry exactly as listed, wildcards
// included, not a test name to match. Returns nullopt if there is no such
// entry.
absl::optional<std::string> ExpectedMessage(absl::string_view entry) const;
private:
FailureListTrieNode entries_;
absl::flat_hash_map<std::string, std::string> expected_messages_;
TestPriority enforcement_level_ = kLowestPriority;
};
} // namespace internal
} // namespace conformance
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_CONFORMANCE_FAILURE_LIST_H__