env_logger_test.cc 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163
  1. // Copyright (c) 2011-present, Facebook, Inc. All rights reserved.
  2. // This source code is licensed under both the GPLv2 (found in the
  3. // COPYING file in the root directory) and Apache 2.0 License
  4. // (found in the LICENSE.Apache file in the root directory).
  5. //
  6. #include "logging/env_logger.h"
  7. #include "test_util/testharness.h"
  8. #include "test_util/testutil.h"
  9. namespace ROCKSDB_NAMESPACE {
  10. namespace {
  11. // In this test we only want to Log some simple log message with
  12. // no format.
  13. void LogMessage(std::shared_ptr<Logger> logger, const std::string& message) {
  14. Log(logger, "%s", message.c_str());
  15. }
  16. // Helper method to write the message num_times in the given logger.
  17. void WriteLogs(std::shared_ptr<Logger> logger, const std::string& message,
  18. int num_times) {
  19. for (int ii = 0; ii < num_times; ++ii) {
  20. LogMessage(logger, message);
  21. }
  22. }
  23. } // namespace
  24. class EnvLoggerTest : public testing::Test {
  25. public:
  26. Env* env_;
  27. EnvLoggerTest() : env_(Env::Default()) {}
  28. ~EnvLoggerTest() = default;
  29. std::shared_ptr<Logger> CreateLogger() {
  30. std::shared_ptr<Logger> result;
  31. assert(NewEnvLogger(kLogFile, env_, &result).ok());
  32. assert(result);
  33. result->SetInfoLogLevel(InfoLogLevel::INFO_LEVEL);
  34. return result;
  35. }
  36. void DeleteLogFile() { ASSERT_OK(env_->DeleteFile(kLogFile)); }
  37. static const std::string kSampleMessage;
  38. static const std::string kTestDir;
  39. static const std::string kLogFile;
  40. };
  41. const std::string EnvLoggerTest::kSampleMessage =
  42. "this is the message to be written to the log file!!";
  43. const std::string EnvLoggerTest::kLogFile = test::PerThreadDBPath("log_file");
  44. TEST_F(EnvLoggerTest, EmptyLogFile) {
  45. auto logger = CreateLogger();
  46. ASSERT_EQ(logger->Close(), Status::OK());
  47. // Check the size of the log file.
  48. uint64_t file_size;
  49. ASSERT_EQ(env_->GetFileSize(kLogFile, &file_size), Status::OK());
  50. ASSERT_EQ(file_size, 0);
  51. DeleteLogFile();
  52. }
  53. TEST_F(EnvLoggerTest, LogMultipleLines) {
  54. auto logger = CreateLogger();
  55. // Write multiple lines.
  56. const int kNumIter = 10;
  57. WriteLogs(logger, kSampleMessage, kNumIter);
  58. // Flush the logs.
  59. logger->Flush();
  60. ASSERT_EQ(logger->Close(), Status::OK());
  61. // Validate whether the log file has 'kNumIter' number of lines.
  62. ASSERT_EQ(test::GetLinesCount(kLogFile, kSampleMessage), kNumIter);
  63. DeleteLogFile();
  64. }
  65. TEST_F(EnvLoggerTest, Overwrite) {
  66. {
  67. auto logger = CreateLogger();
  68. // Write multiple lines.
  69. const int kNumIter = 10;
  70. WriteLogs(logger, kSampleMessage, kNumIter);
  71. ASSERT_EQ(logger->Close(), Status::OK());
  72. // Validate whether the log file has 'kNumIter' number of lines.
  73. ASSERT_EQ(test::GetLinesCount(kLogFile, kSampleMessage), kNumIter);
  74. }
  75. // Now reopen the file again.
  76. {
  77. auto logger = CreateLogger();
  78. // File should be empty.
  79. uint64_t file_size;
  80. ASSERT_EQ(env_->GetFileSize(kLogFile, &file_size), Status::OK());
  81. ASSERT_EQ(file_size, 0);
  82. ASSERT_EQ(logger->GetLogFileSize(), 0);
  83. ASSERT_EQ(logger->Close(), Status::OK());
  84. }
  85. DeleteLogFile();
  86. }
  87. TEST_F(EnvLoggerTest, Close) {
  88. auto logger = CreateLogger();
  89. // Write multiple lines.
  90. const int kNumIter = 10;
  91. WriteLogs(logger, kSampleMessage, kNumIter);
  92. ASSERT_EQ(logger->Close(), Status::OK());
  93. // Validate whether the log file has 'kNumIter' number of lines.
  94. ASSERT_EQ(test::GetLinesCount(kLogFile, kSampleMessage), kNumIter);
  95. DeleteLogFile();
  96. }
  97. TEST_F(EnvLoggerTest, ConcurrentLogging) {
  98. auto logger = CreateLogger();
  99. const int kNumIter = 20;
  100. std::function<void()> cb = [&]() {
  101. WriteLogs(logger, kSampleMessage, kNumIter);
  102. logger->Flush();
  103. };
  104. // Write to the logs from multiple threads.
  105. std::vector<port::Thread> threads;
  106. const int kNumThreads = 5;
  107. // Create threads.
  108. for (int ii = 0; ii < kNumThreads; ++ii) {
  109. threads.emplace_back(cb);
  110. }
  111. // Wait for them to complete.
  112. for (auto& th : threads) {
  113. th.join();
  114. }
  115. ASSERT_EQ(logger->Close(), Status::OK());
  116. // Verfiy the log file.
  117. ASSERT_EQ(test::GetLinesCount(kLogFile, kSampleMessage),
  118. kNumIter * kNumThreads);
  119. DeleteLogFile();
  120. }
  121. } // namespace ROCKSDB_NAMESPACE
  122. int main(int argc, char** argv) {
  123. ROCKSDB_NAMESPACE::port::InstallStackTraceHandler();
  124. ::testing::InitGoogleTest(&argc, argv);
  125. return RUN_ALL_TESTS();
  126. }