LevelDB project 1 10225501460 林子骥 10211900416 郭夏辉
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

100 lines
2.6 KiB

1 month ago
1 month ago
1 month ago
1 month ago
1 month ago
  1. // Copyright (c) 2011 The LevelDB Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file. See the AUTHORS file for names of contributors.
  4. #include "db/builder.h"
  5. #include "db/dbformat.h"
  6. #include "db/filename.h"
  7. #include "db/table_cache.h"
  8. #include "db/version_edit.h"
  9. #include "leveldb/db.h"
  10. #include "leveldb/env.h"
  11. #include "leveldb/iterator.h"
  12. namespace leveldb {
  13. /**
  14. * description: SSTable
  15. * @param dbname
  16. * @param env
  17. * @param options
  18. * @param table_cache
  19. * @param iter
  20. * @param meta sstable的相关元数据
  21. * @return
  22. */
  23. Status BuildTable(const std::string& dbname, Env* env, const Options& options,
  24. TableCache* table_cache, Iterator* iter, FileMetaData* meta) {
  25. Status s;
  26. meta->file_size = 0;
  27. iter->SeekToFirst();
  28. std::string fname = TableFileName(dbname, meta->number);
  29. if (iter->Valid()) {
  30. WritableFile* file;
  31. s = env->NewWritableFile(fname, &file);
  32. if (!s.ok()) {
  33. return s;
  34. }
  35. TableBuilder* builder = new TableBuilder(options, file);
  36. meta->smallest.DecodeFrom(iter->key());//这里是internal_key
  37. auto tmp_ts = DecodeFixed64(iter->value().data() + iter->value().size() - kTSLength);
  38. meta->oldest_ts = tmp_ts;
  39. meta->newer_ts = tmp_ts;
  40. Slice key;
  41. for (; iter->Valid(); iter->Next()) {
  42. key = iter->key();
  43. builder->Add(key, iter->value());
  44. tmp_ts = DecodeFixed64(iter->value().data() + iter->value().size() - kTSLength);
  45. meta->oldest_ts = meta->oldest_ts > tmp_ts ? tmp_ts : meta->oldest_ts;
  46. meta->newer_ts = meta->newer_ts > tmp_ts ? meta->newer_ts : tmp_ts;
  47. }
  48. if (!key.empty()) {
  49. meta->largest.DecodeFrom(key);
  50. }
  51. // Finish and check for builder errors
  52. s = builder->Finish();
  53. if (s.ok()) {
  54. meta->file_size = builder->FileSize();
  55. assert(meta->file_size > 0);
  56. }
  57. delete builder;
  58. // Finish and check for file errors
  59. if (s.ok()) {
  60. s = file->Sync();
  61. }
  62. if (s.ok()) {
  63. s = file->Close();
  64. }
  65. delete file;
  66. file = nullptr;
  67. if (s.ok()) {
  68. // Verify that the table is usable
  69. Iterator* it = table_cache->NewIterator(ReadOptions(), meta->number,
  70. meta->file_size);
  71. s = it->status();
  72. delete it;
  73. }
  74. }
  75. // Check for input iterator errors
  76. if (!iter->status().ok()) {
  77. s = iter->status();
  78. }
  79. if (s.ok() && meta->file_size > 0) {
  80. // Keep it
  81. } else {
  82. env->RemoveFile(fname);
  83. }
  84. return s;
  85. }
  86. } // namespace leveldb