Skip to content

Commit 334ce8f

Browse files
committed
db: initialize more LevelMetrics fields on recovery
We weren't initializing all `LevelMetrics` fields when reading a manifest. This isn't a big deal in practice because on the first version change, we will reinitialize these fields. This change reuses the code that normally sets these fields when updating the version.
1 parent df921f1 commit 334ce8f

File tree

6 files changed

+105
-78
lines changed

6 files changed

+105
-78
lines changed

metrics.go

Lines changed: 12 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -978,19 +978,6 @@ func makeCompressionInfo(algorithm string, table, blob CompressionStatsForSettin
978978
// See testdata/metrics for an example.
979979
func (m *Metrics) String() string {
980980
wb := ascii.Make(128 /* width */, 80 /* height */)
981-
var total LevelMetrics
982-
for l := range numLevels {
983-
total.Add(&m.Levels[l])
984-
}
985-
// Compute total bytes-in as the bytes written to the WAL + bytes ingested.
986-
total.TableBytesIn = m.WAL.BytesWritten + total.TableBytesIngested
987-
// Add the total bytes-in to the total bytes-flushed. This is to account for
988-
// the bytes written to the log and bytes written externally and then
989-
// ingested.
990-
total.TableBytesFlushed += total.TableBytesIn
991-
total.Score = math.NaN()
992-
total.FillFactor = math.NaN()
993-
total.CompensatedFillFactor = math.NaN()
994981

995982
// LSM level metrics.
996983
cur := wb.At(0, 0)
@@ -1165,6 +1152,18 @@ func (m *Metrics) String() string {
11651152
return wb.String()
11661153
}
11671154

1155+
func (m *Metrics) LevelMetricsString() string {
1156+
wb := ascii.Make(128 /* width */, 80 /* height */)
1157+
1158+
// LSM level metrics.
1159+
cur := wb.At(0, 0)
1160+
cur = cur.WriteString(levelMetricsTableTopHeader).NewlineReturn()
1161+
levelMetricsTable.Render(cur, table.RenderOptions{
1162+
HorizontalDividers: table.MakeHorizontalDividers(0, -1),
1163+
}, slices.Collect(m.LevelMetricsIter())...)
1164+
return wb.String()
1165+
}
1166+
11681167
func ifNonZero[T constraints.Integer](v T, s string) string {
11691168
if v > 0 {
11701169
return s

recovery.go

Lines changed: 1 addition & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -300,13 +300,7 @@ func recoverVersion(
300300
MinimumAge: opts.Experimental.ValueSeparationPolicy().RewriteMinimumAge,
301301
})
302302
vs.version = newVersion
303-
304-
for i := range vs.metrics.Levels {
305-
l := &vs.metrics.Levels[i]
306-
l.TablesCount = int64(newVersion.Levels[i].Len())
307-
files := newVersion.Levels[i].Slice()
308-
l.TablesSize = int64(files.TableSizeSum())
309-
}
303+
setBasicLevelMetrics(&vs.metrics, newVersion)
310304
for _, l := range newVersion.Levels {
311305
for f := range l.All() {
312306
if !f.Virtual {

testdata/version_set

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -423,6 +423,16 @@ obsolete tables: 000102
423423
no zombie blob files
424424
no obsolete blob files
425425

426+
metrics
427+
----
428+
LSM | vtables | value sep | | ingested | amp
429+
level size | tables size | count size | refsz valblk | in | tables size | r w
430+
-----------------+--------------+--------------+---------------+--------+--------------+----------
431+
L2 100B | 1 100B | 0 0 | 0B 0B | 0B | 0 0B | 1 0
432+
L3 23KB | 3 2.9KB | 0 0 | 20KB 0B | 0B | 0 0B | 1 0
433+
-----------------+--------------+--------------+---------------+--------+--------------+----------
434+
total 23KB | 4 3KB | 0 0 | 20KB 0B | 0B | 0 0B | 2 0
435+
426436
reopen
427437
----
428438
current version:
@@ -440,6 +450,16 @@ no obsolete tables
440450
no zombie blob files
441451
no obsolete blob files
442452

453+
metrics
454+
----
455+
LSM | vtables | value sep | | ingested | amp
456+
level size | tables size | count size | refsz valblk | in | tables size | r w
457+
-----------------+--------------+--------------+---------------+--------+--------------+----------
458+
L2 100B | 1 100B | 0 0 | 0B 0B | 0B | 0 0B | 1 0
459+
L3 23KB | 3 2.9KB | 0 0 | 20KB 0B | 0B | 0 0B | 1 0
460+
-----------------+--------------+--------------+---------------+--------+--------------+----------
461+
total 23KB | 4 3KB | 0 0 | 20KB 0B | 0B | 0 0B | 2 0
462+
443463
# Delete the referencing table and the blob file. There is no reference to the
444464
# previous Version, so the files should all be immediately obsolete.
445465

tool/testdata/db_lsm

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -14,9 +14,9 @@ db lsm
1414
LSM | vtables | value sep | | ingested | amp
1515
level size | tables size | count size | refsz valblk | in | tables size | r w
1616
-----------------+--------------+--------------+---------------+--------+--------------+----------
17-
L0 709B | 1 709B | 0 0 | 0B 0B | 0B | 0 0B | 0 0
17+
L0 709B | 1 709B | 0 0 | 0B 0B | 0B | 0 0B | 1 0
1818
-----------------+--------------+--------------+---------------+--------+--------------+----------
19-
total 709B | 1 709B | 0 0 | 0B 0B | 0B | 0 0B | 0 0
19+
total 709B | 1 709B | 0 0 | 0B 0B | 0B | 0 0B | 1 0
2020

2121
COMPACTIONS | moved | multilevel | read | written
2222
level | score ff cff | tables size | top in read | tables blob | tables sstsz blobsz
@@ -80,9 +80,9 @@ db lsm --url
8080
LSM | vtables | value sep | | ingested | amp
8181
level size | tables size | count size | refsz valblk | in | tables size | r w
8282
-----------------+--------------+--------------+---------------+--------+--------------+----------
83-
L0 709B | 1 709B | 0 0 | 0B 0B | 0B | 0 0B | 0 0
83+
L0 709B | 1 709B | 0 0 | 0B 0B | 0B | 0 0B | 1 0
8484
-----------------+--------------+--------------+---------------+--------+--------------+----------
85-
total 709B | 1 709B | 0 0 | 0B 0B | 0B | 0 0B | 0 0
85+
total 709B | 1 709B | 0 0 | 0B 0B | 0B | 0 0B | 1 0
8686

8787
COMPACTIONS | moved | multilevel | read | written
8888
level | score ff cff | tables size | top in read | tables blob | tables sstsz blobsz

version_set.go

Lines changed: 50 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -604,45 +604,7 @@ func (vs *versionSet) UpdateVersionLocked(
604604
}
605605

606606
vs.metrics.updateLevelMetrics(vu.Metrics)
607-
for i := range vs.metrics.Levels {
608-
l := &vs.metrics.Levels[i]
609-
l.TablesCount = int64(newVersion.Levels[i].Len())
610-
l.VirtualTablesCount = newVersion.Levels[i].NumVirtual
611-
l.VirtualTablesSize = newVersion.Levels[i].VirtualTableSize
612-
l.TablesSize = int64(newVersion.Levels[i].TableSize())
613-
l.EstimatedReferencesSize = newVersion.Levels[i].EstimatedReferenceSize()
614-
l.Sublevels = 0
615-
if l.TablesCount > 0 {
616-
l.Sublevels = 1
617-
}
618-
if invariants.Enabled {
619-
levelFiles := newVersion.Levels[i].Slice()
620-
if size := int64(levelFiles.TableSizeSum()); l.TablesSize != size {
621-
vs.opts.Logger.Fatalf("versionSet metrics L%d Size = %d, actual size = %d", i, l.TablesSize, size)
622-
}
623-
refSize := uint64(0)
624-
for f := range levelFiles.All() {
625-
refSize += f.EstimatedReferenceSize()
626-
}
627-
if refSize != l.EstimatedReferencesSize {
628-
vs.opts.Logger.Fatalf("versionSet metrics L%d EstimatedReferencesSize = %d, recomputed size = %d", i, l.EstimatedReferencesSize, refSize)
629-
}
630-
631-
if nVirtual := levelFiles.NumVirtual(); nVirtual != l.VirtualTablesCount {
632-
vs.opts.Logger.Fatalf(
633-
"versionSet metrics L%d NumVirtual = %d, actual NumVirtual = %d",
634-
i, l.VirtualTablesCount, nVirtual,
635-
)
636-
}
637-
if vSize := levelFiles.VirtualTableSizeSum(); vSize != l.VirtualTablesSize {
638-
vs.opts.Logger.Fatalf(
639-
"versionSet metrics L%d Virtual size = %d, actual size = %d",
640-
i, l.VirtualTablesSize, vSize,
641-
)
642-
}
643-
}
644-
}
645-
vs.metrics.Levels[0].Sublevels = int32(len(newVersion.L0SublevelFiles))
607+
setBasicLevelMetrics(&vs.metrics, newVersion)
646608
vs.metrics.Table.Local.LiveSize = uint64(int64(vs.metrics.Table.Local.LiveSize) + localTablesLiveDelta.size)
647609
vs.metrics.Table.Local.LiveCount = uint64(int64(vs.metrics.Table.Local.LiveCount) + localTablesLiveDelta.count)
648610
vs.metrics.BlobFiles.Local.LiveSize = uint64(int64(vs.metrics.BlobFiles.Local.LiveSize) + localBlobLiveDelta.size)
@@ -1111,6 +1073,55 @@ func (vs *versionSet) updateObsoleteObjectMetricsLocked() {
11111073
}
11121074
}
11131075

1076+
// This method sets the following fields of m.Levels[*]:
1077+
// - [Virtual]Tables{Count,Size}
1078+
// - Sublevels
1079+
// - EstimatedReferencesSize
1080+
func setBasicLevelMetrics(m *Metrics, newVersion *manifest.Version) {
1081+
for i := range m.Levels {
1082+
l := &m.Levels[i]
1083+
l.TablesCount = int64(newVersion.Levels[i].Len())
1084+
l.TablesSize = int64(newVersion.Levels[i].TableSize())
1085+
l.VirtualTablesCount = newVersion.Levels[i].NumVirtual
1086+
l.VirtualTablesSize = newVersion.Levels[i].VirtualTableSize
1087+
l.EstimatedReferencesSize = newVersion.Levels[i].EstimatedReferenceSize()
1088+
l.Sublevels = 0
1089+
if l.TablesCount > 0 {
1090+
l.Sublevels = 1
1091+
}
1092+
if invariants.Enabled {
1093+
levelFiles := newVersion.Levels[i].Slice()
1094+
if size := int64(levelFiles.TableSizeSum()); l.TablesSize != size {
1095+
panic(fmt.Sprintf("versionSet metrics L%d Size = %d, actual size = %d", i, l.TablesSize, size))
1096+
}
1097+
refSize := uint64(0)
1098+
for f := range levelFiles.All() {
1099+
refSize += f.EstimatedReferenceSize()
1100+
}
1101+
if refSize != l.EstimatedReferencesSize {
1102+
panic(fmt.Sprintf(
1103+
"versionSet metrics L%d EstimatedReferencesSize = %d, recomputed size = %d",
1104+
i, l.EstimatedReferencesSize, refSize,
1105+
))
1106+
}
1107+
1108+
if nVirtual := levelFiles.NumVirtual(); nVirtual != l.VirtualTablesCount {
1109+
panic(fmt.Sprintf(
1110+
"versionSet metrics L%d NumVirtual = %d, actual NumVirtual = %d",
1111+
i, l.VirtualTablesCount, nVirtual,
1112+
))
1113+
}
1114+
if vSize := levelFiles.VirtualTableSizeSum(); vSize != l.VirtualTablesSize {
1115+
panic(fmt.Sprintf(
1116+
"versionSet metrics L%d Virtual size = %d, actual size = %d",
1117+
i, l.VirtualTablesSize, vSize,
1118+
))
1119+
}
1120+
}
1121+
}
1122+
m.Levels[0].Sublevels = int32(len(newVersion.L0SublevelFiles))
1123+
}
1124+
11141125
func findCurrentManifest(
11151126
fs vfs.FS, dirname string, ls []string,
11161127
) (marker *atomicfs.Marker, manifestNum base.DiskFileNum, exists bool, err error) {
@@ -1133,18 +1144,3 @@ func findCurrentManifest(
11331144
}
11341145
return marker, manifestNum, true, nil
11351146
}
1136-
1137-
func newFileMetrics(newFiles []manifest.NewTableEntry) levelMetricsDelta {
1138-
var m levelMetricsDelta
1139-
for _, nf := range newFiles {
1140-
lm := m[nf.Level]
1141-
if lm == nil {
1142-
lm = &LevelMetrics{}
1143-
m[nf.Level] = lm
1144-
}
1145-
lm.TablesCount++
1146-
lm.TablesSize += int64(nf.Meta.Size)
1147-
lm.EstimatedReferencesSize += nf.Meta.EstimatedReferenceSize()
1148-
}
1149-
return m
1150-
}

version_set_test.go

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -232,6 +232,9 @@ func TestVersionSet(t *testing.T) {
232232
}
233233
}
234234

235+
case "metrics":
236+
return vs.metrics.LevelMetricsString()
237+
235238
default:
236239
td.Fatalf(t, "unknown command: %s", td.Cmd)
237240
}
@@ -573,3 +576,18 @@ func TestCrashDuringManifestWrite_LargeKeys(t *testing.T) {
573576
}()
574577
}
575578
}
579+
580+
func newFileMetrics(newFiles []manifest.NewTableEntry) levelMetricsDelta {
581+
var m levelMetricsDelta
582+
for _, nf := range newFiles {
583+
lm := m[nf.Level]
584+
if lm == nil {
585+
lm = &LevelMetrics{}
586+
m[nf.Level] = lm
587+
}
588+
lm.TablesCount++
589+
lm.TablesSize += int64(nf.Meta.Size)
590+
lm.EstimatedReferencesSize += nf.Meta.EstimatedReferenceSize()
591+
}
592+
return m
593+
}

0 commit comments

Comments
 (0)