From c067fd22ebeab03b44dd66593ee53256b2ac1a8c Mon Sep 17 00:00:00 2001 From: coffeegoddd Date: Fri, 17 Jan 2025 12:24:11 -0800 Subject: [PATCH] /go/libraries/doltcore/{doltdb,env}: another optimization --- go/libraries/doltcore/doltdb/doltdb.go | 19 +++++++++++--- go/libraries/doltcore/doltdb/tag.go | 25 +++++++++++++++++++ go/libraries/doltcore/env/actions/tag.go | 13 +++------- go/libraries/doltcore/env/actions/tag_test.go | 1 - 4 files changed, 45 insertions(+), 13 deletions(-) diff --git a/go/libraries/doltcore/doltdb/doltdb.go b/go/libraries/doltcore/doltdb/doltdb.go index 4a137b3dbe..b05564eb37 100644 --- a/go/libraries/doltcore/doltdb/doltdb.go +++ b/go/libraries/doltcore/doltdb/doltdb.go @@ -88,6 +88,13 @@ type DoltDB struct { databaseName string } +type TagRefWithMeta struct { + TagRef ref.TagRef + Meta *datas.TagMeta + CommitAddr hash.Hash + MaybeHeadAddr hash.Hash +} + // DoltDBFromCS creates a DoltDB from a noms chunks.ChunkStore func DoltDBFromCS(cs chunks.ChunkStore, databaseName string) *DoltDB { vrw := types.NewValueStore(cs) @@ -594,8 +601,13 @@ func (ddb *DoltDB) ResolveTag(ctx context.Context, tagRef ref.TagRef) (*Tag, err return NewTag(ctx, tagRef.GetPath(), ds, ddb.vrw, ddb.ns) } +// ResolveTag takes a TagRef and returns the corresponding Tag object. +func (ddb *DoltDB) ResolveTagFromTagRefWithMeta(ctx context.Context, tagRefWithMeta *TagRefWithMeta) (*Tag, error) { + return NewTagFromTagRefWithMeta(ctx, tagRefWithMeta.TagRef.GetPath(), tagRefWithMeta, ddb.vrw, ddb.ns) +} + // ResolveTagMeta takes a TagRef and returns the corresponding TagMeta object. -func (ddb *DoltDB) ResolveTagMeta(ctx context.Context, tagRef ref.TagRef) (*datas.TagMeta, error) { +func (ddb *DoltDB) ResolveTagMeta(ctx context.Context, tagRef ref.TagRef) (*TagRefWithMeta, error) { ds, err := ddb.db.GetDataset(ctx, tagRef.String()) if err != nil { return nil, ErrTagNotFound @@ -609,12 +621,13 @@ func (ddb *DoltDB) ResolveTagMeta(ctx context.Context, tagRef ref.TagRef) (*data return nil, fmt.Errorf("tagRef head is not a tag") } - meta, _, err := ds.HeadTag() + meta, commitAddr, err := ds.HeadTag() if err != nil { return nil, err } - return meta, nil + addr, _ := ds.MaybeHeadAddr() + return &TagRefWithMeta{TagRef: tagRef, Meta: meta, CommitAddr: commitAddr, MaybeHeadAddr: addr}, nil } // ResolveWorkingSet takes a WorkingSetRef and returns the corresponding WorkingSet object. diff --git a/go/libraries/doltcore/doltdb/tag.go b/go/libraries/doltcore/doltdb/tag.go index 2186e8bd91..a85e2fc028 100644 --- a/go/libraries/doltcore/doltdb/tag.go +++ b/go/libraries/doltcore/doltdb/tag.go @@ -32,6 +32,31 @@ type Tag struct { Commit *Commit } +// NewTagFromTagRefWithMeta creates a new Tag object from a TagRefWithMeta. +func NewTagFromTagRefWithMeta(ctx context.Context, name string, tagRefWithMeta *TagRefWithMeta, vrw types.ValueReadWriter, ns tree.NodeStore) (*Tag, error) { + dc, err := datas.LoadCommitAddr(ctx, vrw, tagRefWithMeta.CommitAddr) + if err != nil { + return nil, err + } + + if dc.IsGhost() { + return nil, ErrGhostCommitEncountered + } + + commit, err := NewCommit(ctx, vrw, ns, dc) + if err != nil { + return nil, err + } + + return &Tag{ + Name: name, + vrw: vrw, + addr: tagRefWithMeta.MaybeHeadAddr, + Meta: tagRefWithMeta.Meta, + Commit: commit, + }, nil +} + // NewTag creates a new Tag object. func NewTag(ctx context.Context, name string, ds datas.Dataset, vrw types.ValueReadWriter, ns tree.NodeStore) (*Tag, error) { meta, commitAddr, err := ds.HeadTag() diff --git a/go/libraries/doltcore/env/actions/tag.go b/go/libraries/doltcore/env/actions/tag.go index bc801bc13e..9d68803003 100644 --- a/go/libraries/doltcore/env/actions/tag.go +++ b/go/libraries/doltcore/env/actions/tag.go @@ -139,11 +139,6 @@ func IterResolvedTags(ctx context.Context, ddb *doltdb.DoltDB, cb func(tag *dolt return nil } -type TagRefWithMeta struct { - TagRef ref.TagRef - Meta *datas.TagMeta -} - const DefaultPageSize = 100 // IterResolvedTagsPaginated iterates over tags in dEnv.DoltDB from newest to oldest, resolving the tag to a commit and calling cb(). @@ -155,17 +150,17 @@ func IterResolvedTagsPaginated(ctx context.Context, ddb *doltdb.DoltDB, startTag } // for each tag, get the meta - tagMetas := make([]*TagRefWithMeta, 0, len(tagRefs)) + tagMetas := make([]*doltdb.TagRefWithMeta, 0, len(tagRefs)) for _, r := range tagRefs { tr, ok := r.(ref.TagRef) if !ok { return "", fmt.Errorf("DoltDB.GetTags() returned non-tag DoltRef") } - meta, err := ddb.ResolveTagMeta(ctx, tr) + tm, err := ddb.ResolveTagMeta(ctx, tr) if err != nil { return "", err } - tagMetas = append(tagMetas, &TagRefWithMeta{TagRef: tr, Meta: meta}) + tagMetas = append(tagMetas, tm) } // sort by meta timestamp @@ -194,7 +189,7 @@ func IterResolvedTagsPaginated(ctx context.Context, ddb *doltdb.DoltDB, startTag // resolve tags for this page for _, tm := range pageTagMetas { - tag, err := ddb.ResolveTag(ctx, tm.TagRef) + tag, err := ddb.ResolveTagFromTagRefWithMeta(ctx, tm) if err != nil { return "", err } diff --git a/go/libraries/doltcore/env/actions/tag_test.go b/go/libraries/doltcore/env/actions/tag_test.go index 614e54601f..508d7fcb04 100644 --- a/go/libraries/doltcore/env/actions/tag_test.go +++ b/go/libraries/doltcore/env/actions/tag_test.go @@ -68,7 +68,6 @@ func TestVisitResolvedTag(t *testing.T) { }) require.Equal(t, doltdb.ErrTagNotFound, err) } - func TestIterResolvedTagsPaginated(t *testing.T) { dEnv, _ := createTestEnv() ctx := context.Background()