From aa6178524303d0842d6c8fcd6c52660a0fc8cf56 Mon Sep 17 00:00:00 2001 From: Lei Da Date: Tue, 19 Nov 2024 14:26:43 +0800 Subject: [PATCH 1/4] add unit test for tag store --- builder/store/database/tag.go | 44 +- builder/store/database/tag_test.go | 673 +++++++++++++++++++++++++++++ 2 files changed, 678 insertions(+), 39 deletions(-) create mode 100644 builder/store/database/tag_test.go diff --git a/builder/store/database/tag.go b/builder/store/database/tag.go index 424f644c..9e51a241 100644 --- a/builder/store/database/tag.go +++ b/builder/store/database/tag.go @@ -6,7 +6,6 @@ import ( "errors" "fmt" "log/slog" - "slices" "github.com/uptrace/bun" "opencsg.com/csghub-server/common/types" @@ -34,7 +33,6 @@ type TagStore interface { AllSpaceCategories(ctx context.Context) ([]TagCategory, error) CreateTag(ctx context.Context, category, name, group string, scope TagScope) (Tag, error) SaveTags(ctx context.Context, tags []*Tag) error - UpsertTags(ctx context.Context, tagScope TagScope, categoryTagMap map[string][]string) ([]Tag, error) // SetMetaTags will delete existing tags and create new ones SetMetaTags(ctx context.Context, repoType types.RepositoryType, namespace, name string, tags []*Tag) (repoTags []*RepositoryTag, err error) SetLibraryTag(ctx context.Context, repoType types.RepositoryType, namespace, name string, newTag, oldTag *Tag) (err error) @@ -204,35 +202,6 @@ func (ts *tagStoreImpl) SaveTags(ctx context.Context, tags []*Tag) error { return nil } -func (ts *tagStoreImpl) UpsertTags(ctx context.Context, tagScope TagScope, categoryTagMap map[string][]string) ([]Tag, error) { - var tags []Tag - for category, tagNames := range categoryTagMap { - ctags := make([]Tag, 0) - err := ts.db.Operator.Core.NewSelect().Model(&ctags). - Where("caregory = ? and scope = ?", category, tagScope). - Scan(ctx) - if err != nil { - slog.Error("Failed to select tags", slog.String("category", category), - slog.Any("scope", tagScope), slog.Any("error", err.Error())) - return nil, fmt.Errorf("failed to select tags, cause: %w", err) - } - tags = append(tags, ctags...) - for _, tagName := range tagNames { - if !slices.ContainsFunc(tags, func(t Tag) bool { return t.Name == tagName }) { - newTag, err := ts.CreateTag(ctx, category, tagName, defaultTagGroup, tagScope) - if err != nil { - slog.Error("Failed to create new tag", slog.String("category", category), slog.String("tagName", tagName), - slog.Any("scope", tagScope), slog.Any("error", err.Error)) - return nil, fmt.Errorf("failed to create new tag, cause: %w", err) - } - tags = append(tags, newTag) - } - } - } - - return tags, nil -} - // SetMetaTags will delete existing tags and create new ones func (ts *tagStoreImpl) SetMetaTags(ctx context.Context, repoType types.RepositoryType, namespace, name string, tags []*Tag) (repoTags []*RepositoryTag, err error) { repo := new(Repository) @@ -376,13 +345,10 @@ func (ts *tagStoreImpl) RemoveRepoTags(ctx context.Context, repoID int64, tagIDs if len(tagIDs) == 0 { return nil } - err = ts.db.Operator.Core.RunInTx(ctx, nil, func(ctx context.Context, tx bun.Tx) error { - _, err = tx.NewDelete(). - Model(&RepositoryTag{}). - Where("repository_id =? and tag_id in (?)", repoID, bun.In(tagIDs)). - Exec(ctx) - return err - }) + _, err = ts.db.Operator.Core.NewDelete(). + Model(&RepositoryTag{}). + Where("repository_id =? and tag_id in (?)", repoID, bun.In(tagIDs)). + Exec(ctx) return err } @@ -402,5 +368,5 @@ func (ts *tagStoreImpl) FindOrCreate(ctx context.Context, tag Tag) (*Tag, error) if err != nil { return nil, err } - return &resTag, err + return &tag, err } diff --git a/builder/store/database/tag_test.go b/builder/store/database/tag_test.go new file mode 100644 index 00000000..7e950c6c --- /dev/null +++ b/builder/store/database/tag_test.go @@ -0,0 +1,673 @@ +package database_test + +import ( + "context" + "fmt" + "testing" + "time" + + "github.com/google/uuid" + "github.com/stretchr/testify/require" + "opencsg.com/csghub-server/builder/store/database" + "opencsg.com/csghub-server/common/tests" + "opencsg.com/csghub-server/common/types" +) + +func TestTag_FindOrCreate(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + ts := database.NewTagStoreWithDB(db) + uuid := uuid.New().String() + tag := database.Tag{ + Name: "tag_" + uuid, + Category: "task", + Group: "", + Scope: "model", + BuiltIn: true, + ShowName: "Tag One", + } + newTag, err := ts.FindOrCreate(ctx, tag) + require.Empty(t, err) + require.NotEmpty(t, newTag.ID) + require.Equal(t, tag.Name, newTag.Name) + + existingTag, err := ts.FindOrCreate(ctx, tag) + require.Empty(t, err) + require.Equal(t, newTag.ID, existingTag.ID) +} + +// TestAllTags tests the AllTags method +func TestAllTags(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + var err error + //clear all existing data + _, err = db.Core.NewDelete().Model(&database.Tag{}).Where("1=1").Exec(ctx) + require.Empty(t, err) + + ts := database.NewTagStoreWithDB(db) + tags, err := ts.AllTags(ctx) + require.Empty(t, err) + require.Equal(t, 0, len(tags)) + + var newTags []*database.Tag + newTags = append(newTags, &database.Tag{ + Name: "tag_" + uuid.NewString(), + Category: "task", + Group: "", + Scope: database.ModelTagScope, + BuiltIn: true, + ShowName: "tag one", + }) + newTags = append(newTags, &database.Tag{ + Name: "tag_" + uuid.NewString(), + Category: "task", + Group: "", + Scope: database.ModelTagScope, + BuiltIn: true, + ShowName: "tag one", + }) + err = ts.SaveTags(ctx, newTags) + require.Empty(t, err) + + tags, err = ts.AllTags(ctx) + require.Empty(t, err) + require.Equal(t, 2, len(tags)) +} + +// TestAllTagsByScope tests the AllTagsByScope method +func TestAllTagsByScope(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + ts := database.NewTagStoreWithDB(db) + _, err := ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", "test_scope") + require.Empty(t, err) + _, err = ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", "test_scope") + require.Empty(t, err) + + tags, err := ts.AllTagsByScope(ctx, "test_scope") + require.Empty(t, err) + require.Len(t, tags, 2) + require.Equal(t, string(tags[0].Scope), "test_scope") + require.Equal(t, string(tags[1].Scope), "test_scope") +} + +// TestAllTagsByScopeAndCategory tests the AllTagsByScopeAndCategory method +func TestAllTagsByScopeAndCategory(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + ts := database.NewTagStoreWithDB(db) + _, err := ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", "test_scope") + require.Empty(t, err) + _, err = ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", "test_scope") + require.Empty(t, err) + + tags, err := ts.AllTagsByScopeAndCategory(ctx, "test_scope", "task") + require.Empty(t, err) + require.Len(t, tags, 1) + require.Equal(t, string(tags[0].Scope), "test_scope") +} + +// TestGetTagsByScopeAndCategories tests the GetTagsByScopeAndCategories method +func TestGetTagsByScopeAndCategories(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + ts := database.NewTagStoreWithDB(db) + _, err := ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", "test_scope") + require.Empty(t, err) + _, err = ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", "test_scope") + require.Empty(t, err) + _, err = ts.CreateTag(ctx, "test_category", "tag_"+uuid.New().String(), "Group One", "test_scope") + require.Empty(t, err) + + tags, err := ts.GetTagsByScopeAndCategories(ctx, "test_scope", []string{"task", "library"}) + require.Empty(t, err) + require.Len(t, tags, 2) +} + +// TestAllModelTags tests the AllModelTags method +func TestAllModelTags(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + var err error + //clear all existing data + _, err = db.Core.NewDelete().Model(&database.Tag{}).Where("1=1").Exec(ctx) + require.Empty(t, err) + + ts := database.NewTagStoreWithDB(db) + tags, err := ts.AllModelTags(ctx) + require.Empty(t, err) + require.Len(t, tags, 0) + + _, err = ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", database.ModelTagScope) + require.Empty(t, err) + _, err = ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", database.DatasetTagScope) + require.Empty(t, err) + + tags, err = ts.AllModelTags(ctx) + require.Empty(t, err) + require.Len(t, tags, 1) + +} + +// TestAllPromptTags tests the AllPromptTags method +func TestAllPromptTags(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + var err error + //clear all existing data + _, err = db.Core.NewDelete().Model(&database.Tag{}).Where("1=1").Exec(ctx) + require.Empty(t, err) + + ts := database.NewTagStoreWithDB(db) + tags, err := ts.AllPromptTags(ctx) + require.Empty(t, err) + require.Len(t, tags, 0) + + _, err = ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", database.PromptTagScope) + require.Empty(t, err) + _, err = ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", database.DatasetTagScope) + require.Empty(t, err) + + tags, err = ts.AllPromptTags(ctx) + require.Empty(t, err) + require.Len(t, tags, 1) + +} + +// TestAllDatasetTags tests the AllDatasetTags method +func TestAllDatasetTags(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + var err error + //clear all existing data + _, err = db.Core.NewDelete().Model(&database.Tag{}).Where("1=1").Exec(ctx) + require.Empty(t, err) + + ts := database.NewTagStoreWithDB(db) + tags, err := ts.AllDatasetTags(ctx) + require.Empty(t, err) + require.Len(t, tags, 0) + + _, err = ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", database.PromptTagScope) + require.Empty(t, err) + _, err = ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", database.DatasetTagScope) + require.Empty(t, err) + + tags, err = ts.AllDatasetTags(ctx) + require.Empty(t, err) + require.Len(t, tags, 1) + +} + +// TestAllCodeTags tests the AllCodeTags method +func TestAllCodeTags(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + var err error + //clear all existing data + _, err = db.Core.NewDelete().Model(&database.Tag{}).Where("1=1").Exec(ctx) + require.Empty(t, err) + + ts := database.NewTagStoreWithDB(db) + tags, err := ts.AllCodeTags(ctx) + require.Empty(t, err) + require.Len(t, tags, 0) + + _, err = ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", database.CodeTagScope) + require.Empty(t, err) + _, err = ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", database.DatasetTagScope) + require.Empty(t, err) + + tags, err = ts.AllCodeTags(ctx) + require.Empty(t, err) + require.Len(t, tags, 1) + +} + +// TestAllSpaceTags tests the AllSpaceTags method +func TestAllSpaceTags(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + var err error + //clear all existing data + _, err = db.Core.NewDelete().Model(&database.Tag{}).Where("1=1").Exec(ctx) + require.Empty(t, err) + + ts := database.NewTagStoreWithDB(db) + tags, err := ts.AllSpaceTags(ctx) + require.Empty(t, err) + require.Len(t, tags, 0) + + _, err = ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", database.SpaceTagScope) + require.Empty(t, err) + _, err = ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", database.DatasetTagScope) + require.Empty(t, err) + + tags, err = ts.AllSpaceTags(ctx) + require.Empty(t, err) + require.Len(t, tags, 1) + +} + +// TestAllModelCategories tests the AllModelCategories method +func TestAllModelCategories(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + var err error + //clear all existing data + _, err = db.Core.NewDelete().Model(&database.TagCategory{}).Where("1=1").Exec(ctx) + require.Empty(t, err) + + ts := database.NewTagStoreWithDB(db) + tags, err := ts.AllModelCategories(ctx) + require.Empty(t, err) + require.Len(t, tags, 0) + + tc1 := &database.TagCategory{ + Name: "tc_1", + Scope: database.ModelTagScope, + } + tc2 := &database.TagCategory{ + Name: "tc_2", + Scope: database.DatasetTagScope, + } + _, err = db.Core.NewInsert().Model(tc1).Exec(ctx) + require.Empty(t, err) + _, err = db.Core.NewInsert().Model(tc2).Exec(ctx) + require.Empty(t, err) + + tags, err = ts.AllModelCategories(ctx) + require.Empty(t, err) + require.Len(t, tags, 1) +} + +// TestAllPromptCategories tests the AllPromptCategories method +func TestAllPromptCategories(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + var err error + //clear all existing data + _, err = db.Core.NewDelete().Model(&database.TagCategory{}).Where("1=1").Exec(ctx) + require.Empty(t, err) + + ts := database.NewTagStoreWithDB(db) + tags, err := ts.AllPromptCategories(ctx) + require.Empty(t, err) + require.Len(t, tags, 0) + + tc1 := &database.TagCategory{ + Name: "tc_1", + Scope: database.ModelTagScope, + } + tc2 := &database.TagCategory{ + Name: "tc_2", + Scope: database.PromptTagScope, + } + _, err = db.Core.NewInsert().Model(tc1).Exec(ctx) + require.Empty(t, err) + _, err = db.Core.NewInsert().Model(tc2).Exec(ctx) + require.Empty(t, err) + + tags, err = ts.AllPromptCategories(ctx) + require.Empty(t, err) + require.Len(t, tags, 1) +} + +// TestAllDatasetCategories tests the AllDatasetCategories method +func TestAllDatasetCategories(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + var err error + //clear all existing data + _, err = db.Core.NewDelete().Model(&database.TagCategory{}).Where("1=1").Exec(ctx) + require.Empty(t, err) + + ts := database.NewTagStoreWithDB(db) + tags, err := ts.AllDatasetCategories(ctx) + require.Empty(t, err) + require.Len(t, tags, 0) + + tc1 := &database.TagCategory{ + Name: "tc_1", + Scope: database.ModelTagScope, + } + tc2 := &database.TagCategory{ + Name: "tc_2", + Scope: database.DatasetTagScope, + } + _, err = db.Core.NewInsert().Model(tc1).Exec(ctx) + require.Empty(t, err) + _, err = db.Core.NewInsert().Model(tc2).Exec(ctx) + require.Empty(t, err) + + tags, err = ts.AllDatasetCategories(ctx) + require.Empty(t, err) + require.Len(t, tags, 1) +} + +// TestAllCodeCategories tests the AllCodeCategories method +func TestAllCodeCategories(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + var err error + //clear all existing data + _, err = db.Core.NewDelete().Model(&database.TagCategory{}).Where("1=1").Exec(ctx) + require.Empty(t, err) + + ts := database.NewTagStoreWithDB(db) + tags, err := ts.AllCodeCategories(ctx) + require.Empty(t, err) + require.Len(t, tags, 0) + + tc1 := &database.TagCategory{ + Name: "tc_1", + Scope: database.ModelTagScope, + } + tc2 := &database.TagCategory{ + Name: "tc_2", + Scope: database.CodeTagScope, + } + _, err = db.Core.NewInsert().Model(tc1).Exec(ctx) + require.Empty(t, err) + _, err = db.Core.NewInsert().Model(tc2).Exec(ctx) + require.Empty(t, err) + + tags, err = ts.AllCodeCategories(ctx) + require.Empty(t, err) + require.Len(t, tags, 1) +} + +// TestAllSpaceCategories tests the AllSpaceCategories method +func TestAllSpaceCategories(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + var err error + //clear all existing data + _, err = db.Core.NewDelete().Model(&database.TagCategory{}).Where("1=1").Exec(ctx) + require.Empty(t, err) + + ts := database.NewTagStoreWithDB(db) + tags, err := ts.AllSpaceCategories(ctx) + require.Empty(t, err) + require.Len(t, tags, 0) + + tc1 := &database.TagCategory{ + Name: "tc_1", + Scope: database.ModelTagScope, + } + tc2 := &database.TagCategory{ + Name: "tc_2", + Scope: database.SpaceTagScope, + } + _, err = db.Core.NewInsert().Model(tc1).Exec(ctx) + require.Empty(t, err) + _, err = db.Core.NewInsert().Model(tc2).Exec(ctx) + require.Empty(t, err) + + tags, err = ts.AllSpaceCategories(ctx) + require.Empty(t, err) + require.Len(t, tags, 1) +} + +// TestCreateTag tests the CreateTag method +func TestCreateTag(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + var err error + ts := database.NewTagStoreWithDB(db) + t1, err := ts.CreateTag(ctx, "task", "tag_"+uuid.NewString(), "", database.ModelTagScope) + require.Empty(t, err) + require.NotEmpty(t, t1.ID) +} + +// TestSetMetaTags tests the SetMetaTags method +func TestSetMetaTags(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + // insert a new repo + rs := database.NewRepoStoreWithDB(db) + userName := "user_name_" + uuid.NewString() + repoName := "repo_name_" + uuid.NewString() + repo, err := rs.CreateRepo(ctx, database.Repository{ + UserID: 1, + Path: fmt.Sprintf("%s/%s", userName, repoName), + GitPath: fmt.Sprintf("models_%s/%s", userName, repoName), + Name: repoName, + Nickname: "", + Description: "", + Private: false, + RepositoryType: types.ModelRepo, + }) + require.Empty(t, err) + require.NotNil(t, repo) + + ts := database.NewTagStoreWithDB(db) + var tags []*database.Tag + tags = append(tags, &database.Tag{ + Name: "tag_" + uuid.NewString(), + Category: "task", + Group: "", + Scope: database.ModelTagScope, + BuiltIn: true, + ShowName: "", + }) + tags = append(tags, &database.Tag{ + Name: "tag_" + uuid.NewString(), + Category: "framework", + Group: "", + Scope: database.ModelTagScope, + BuiltIn: true, + ShowName: "", + }) + repoTags, err := ts.SetMetaTags(ctx, types.ModelRepo, userName, repoName, tags) + // should report err as framework tag is not allowed + require.NotEmpty(t, err) + + tags = tags[:1] + repoTags, err = ts.SetMetaTags(ctx, types.ModelRepo, userName, repoName, tags) + require.Empty(t, err) + require.Len(t, repoTags, 1) +} + +// TestSetLibraryTag tests the SetLibraryTag method +func TestSetLibraryTag(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + // insert a new repo + rs := database.NewRepoStoreWithDB(db) + userName := "user_name_" + uuid.NewString() + repoName := "repo_name_" + uuid.NewString() + repo, err := rs.CreateRepo(ctx, database.Repository{ + UserID: 1, + Path: fmt.Sprintf("%s/%s", userName, repoName), + GitPath: fmt.Sprintf("models_%s/%s", userName, repoName), + Name: repoName, + Nickname: "", + Description: "", + Private: false, + RepositoryType: types.ModelRepo, + }) + require.Empty(t, err) + require.NotNil(t, repo) + + ts := database.NewTagStoreWithDB(db) + oldTag, err := ts.CreateTag(ctx, "task", "tag_"+uuid.NewString(), "", database.ModelTagScope) + require.Empty(t, err) + newTag, err := ts.CreateTag(ctx, "task", "tag_"+uuid.NewString(), "", database.ModelTagScope) + require.Empty(t, err) + + err = ts.SetLibraryTag(ctx, types.ModelRepo, userName, repoName, &newTag, &oldTag) + require.Empty(t, err) + + repoTagStore := database.NewRepoStoreWithDB(db) + tags, err := repoTagStore.Tags(ctx, repo.ID) + require.Empty(t, err) + require.Len(t, tags, 1) +} + +// TestUpsertRepoTags tests the UpsertRepoTags method +func TestUpsertRepoTags(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + ts := database.NewTagStoreWithDB(db) + oldTag, err := ts.CreateTag(ctx, "task", "tag_"+uuid.NewString(), "", database.ModelTagScope) + require.Empty(t, err) + + // insert a new repo with tags + rs := database.NewRepoStoreWithDB(db) + userName := "user_name_" + uuid.NewString() + repoName := "repo_name_" + uuid.NewString() + repo, err := rs.CreateRepo(ctx, database.Repository{ + UserID: 1, + Path: fmt.Sprintf("%s/%s", userName, repoName), + GitPath: fmt.Sprintf("models_%s/%s", userName, repoName), + Name: repoName, + Nickname: "", + Description: "", + Private: false, + RepositoryType: types.ModelRepo, + Tags: []database.Tag{oldTag}, + }) + require.Empty(t, err) + require.NotNil(t, repo) + require.Len(t, repo.Tags, 1) + + oldTagIds := make([]int64, 0, len(repo.Tags)) + oldTagIds = append(oldTagIds, repo.Tags[0].ID) + + newTag, err := ts.CreateTag(ctx, "task", "tag_"+uuid.NewString(), "", database.ModelTagScope) + require.Empty(t, err) + newTagIds := make([]int64, 0, 2) + newTagIds = append(newTagIds, newTag.ID) + newTagIds = append(newTagIds, oldTag.ID) + + err = ts.UpsertRepoTags(ctx, repo.ID, oldTagIds, newTagIds) + require.Empty(t, err) + repoTags, err := rs.Tags(ctx, repo.ID) + require.Empty(t, err) + require.Len(t, repoTags, 2) +} + +// TestRemoveRepoTags tests the RemoveRepoTags method +func TestRemoveRepoTags(t *testing.T) { + db := tests.InitTestDB() + defer db.Close() + + ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) + defer cancel() + + ts := database.NewTagStoreWithDB(db) + tag1, err := ts.CreateTag(ctx, "task", "tag_"+uuid.NewString(), "", database.ModelTagScope) + require.Empty(t, err) + require.NotEmpty(t, tag1.ID) + tag2, err := ts.CreateTag(ctx, "task", "tag_"+uuid.NewString(), "", database.ModelTagScope) + require.Empty(t, err) + require.NotEmpty(t, tag2.ID) + + // insert a new repo with tags + rs := database.NewRepoStoreWithDB(db) + userName := "user_name_" + uuid.NewString() + repoName := "repo_name_" + uuid.NewString() + repo, err := rs.CreateRepo(ctx, database.Repository{ + UserID: 1, + Path: fmt.Sprintf("%s/%s", userName, repoName), + GitPath: fmt.Sprintf("models_%s/%s", userName, repoName), + Name: repoName, + Nickname: "", + Description: "", + Private: false, + RepositoryType: types.ModelRepo, + }) + require.Empty(t, err) + require.NotNil(t, repo) + // set repo tags + ts.UpsertRepoTags(ctx, repo.ID, []int64{}, []int64{tag1.ID, tag2.ID}) + + removeTagIds := make([]int64, 0, 1) + removeTagIds = append(removeTagIds, tag2.ID) + + err = ts.RemoveRepoTags(ctx, repo.ID, removeTagIds) + require.Empty(t, err) + repoTags, err := rs.Tags(ctx, repo.ID) + require.Empty(t, err) + require.Len(t, repoTags, 1) + require.EqualValues(t, repoTags[0], tag1) + +} From 100d2776ffe15541c428de98827ec466c590c4eb Mon Sep 17 00:00:00 2001 From: Lei Da Date: Tue, 19 Nov 2024 15:03:48 +0800 Subject: [PATCH 2/4] change tag store ut function name --- builder/store/database/tag_test.go | 40 +++++++++++++++--------------- 1 file changed, 20 insertions(+), 20 deletions(-) diff --git a/builder/store/database/tag_test.go b/builder/store/database/tag_test.go index 7e950c6c..552dd80f 100644 --- a/builder/store/database/tag_test.go +++ b/builder/store/database/tag_test.go @@ -13,7 +13,7 @@ import ( "opencsg.com/csghub-server/common/types" ) -func TestTag_FindOrCreate(t *testing.T) { +func TestTagStore_FindOrCreate(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -41,7 +41,7 @@ func TestTag_FindOrCreate(t *testing.T) { } // TestAllTags tests the AllTags method -func TestAllTags(t *testing.T) { +func TestTagStore_AllTags(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -84,7 +84,7 @@ func TestAllTags(t *testing.T) { } // TestAllTagsByScope tests the AllTagsByScope method -func TestAllTagsByScope(t *testing.T) { +func TestTagStore_AllTagsByScope(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -105,7 +105,7 @@ func TestAllTagsByScope(t *testing.T) { } // TestAllTagsByScopeAndCategory tests the AllTagsByScopeAndCategory method -func TestAllTagsByScopeAndCategory(t *testing.T) { +func TestTagStore_AllTagsByScopeAndCategory(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -125,7 +125,7 @@ func TestAllTagsByScopeAndCategory(t *testing.T) { } // TestGetTagsByScopeAndCategories tests the GetTagsByScopeAndCategories method -func TestGetTagsByScopeAndCategories(t *testing.T) { +func TestTagStore_GetTagsByScopeAndCategories(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -146,7 +146,7 @@ func TestGetTagsByScopeAndCategories(t *testing.T) { } // TestAllModelTags tests the AllModelTags method -func TestAllModelTags(t *testing.T) { +func TestTagStore_AllModelTags(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -175,7 +175,7 @@ func TestAllModelTags(t *testing.T) { } // TestAllPromptTags tests the AllPromptTags method -func TestAllPromptTags(t *testing.T) { +func TestTagStore_AllPromptTags(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -204,7 +204,7 @@ func TestAllPromptTags(t *testing.T) { } // TestAllDatasetTags tests the AllDatasetTags method -func TestAllDatasetTags(t *testing.T) { +func TestTagStore_AllDatasetTags(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -233,7 +233,7 @@ func TestAllDatasetTags(t *testing.T) { } // TestAllCodeTags tests the AllCodeTags method -func TestAllCodeTags(t *testing.T) { +func TestTagStore_AllCodeTags(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -262,7 +262,7 @@ func TestAllCodeTags(t *testing.T) { } // TestAllSpaceTags tests the AllSpaceTags method -func TestAllSpaceTags(t *testing.T) { +func TestTagStore_AllSpaceTags(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -291,7 +291,7 @@ func TestAllSpaceTags(t *testing.T) { } // TestAllModelCategories tests the AllModelCategories method -func TestAllModelCategories(t *testing.T) { +func TestTagStore_AllModelCategories(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -327,7 +327,7 @@ func TestAllModelCategories(t *testing.T) { } // TestAllPromptCategories tests the AllPromptCategories method -func TestAllPromptCategories(t *testing.T) { +func TestTagStore_AllPromptCategories(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -363,7 +363,7 @@ func TestAllPromptCategories(t *testing.T) { } // TestAllDatasetCategories tests the AllDatasetCategories method -func TestAllDatasetCategories(t *testing.T) { +func TestTagStore_AllDatasetCategories(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -399,7 +399,7 @@ func TestAllDatasetCategories(t *testing.T) { } // TestAllCodeCategories tests the AllCodeCategories method -func TestAllCodeCategories(t *testing.T) { +func TestTagStore_AllCodeCategories(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -435,7 +435,7 @@ func TestAllCodeCategories(t *testing.T) { } // TestAllSpaceCategories tests the AllSpaceCategories method -func TestAllSpaceCategories(t *testing.T) { +func TestTagStore_AllSpaceCategories(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -471,7 +471,7 @@ func TestAllSpaceCategories(t *testing.T) { } // TestCreateTag tests the CreateTag method -func TestCreateTag(t *testing.T) { +func TestTagStore_CreateTag(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -486,7 +486,7 @@ func TestCreateTag(t *testing.T) { } // TestSetMetaTags tests the SetMetaTags method -func TestSetMetaTags(t *testing.T) { +func TestTagStore_SetMetaTags(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -539,7 +539,7 @@ func TestSetMetaTags(t *testing.T) { } // TestSetLibraryTag tests the SetLibraryTag method -func TestSetLibraryTag(t *testing.T) { +func TestTagStore_SetLibraryTag(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -579,7 +579,7 @@ func TestSetLibraryTag(t *testing.T) { } // TestUpsertRepoTags tests the UpsertRepoTags method -func TestUpsertRepoTags(t *testing.T) { +func TestTagStore_UpsertRepoTags(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -626,7 +626,7 @@ func TestUpsertRepoTags(t *testing.T) { } // TestRemoveRepoTags tests the RemoveRepoTags method -func TestRemoveRepoTags(t *testing.T) { +func TestTagStore_RemoveRepoTags(t *testing.T) { db := tests.InitTestDB() defer db.Close() From ff8272a905974d2605f0eb712a7a9c9b3ff8d665 Mon Sep 17 00:00:00 2001 From: Lei Da Date: Thu, 21 Nov 2024 14:36:11 +0800 Subject: [PATCH 3/4] refactor tag store unit tests --- builder/store/database/tag_test.go | 200 +++++------------------------ 1 file changed, 35 insertions(+), 165 deletions(-) diff --git a/builder/store/database/tag_test.go b/builder/store/database/tag_test.go index 552dd80f..e60113bb 100644 --- a/builder/store/database/tag_test.go +++ b/builder/store/database/tag_test.go @@ -40,7 +40,6 @@ func TestTagStore_FindOrCreate(t *testing.T) { require.Equal(t, newTag.ID, existingTag.ID) } -// TestAllTags tests the AllTags method func TestTagStore_AllTags(t *testing.T) { db := tests.InitTestDB() defer db.Close() @@ -58,29 +57,45 @@ func TestTagStore_AllTags(t *testing.T) { require.Empty(t, err) require.Equal(t, 0, len(tags)) - var newTags []*database.Tag - newTags = append(newTags, &database.Tag{ - Name: "tag_" + uuid.NewString(), - Category: "task", - Group: "", - Scope: database.ModelTagScope, - BuiltIn: true, - ShowName: "tag one", - }) - newTags = append(newTags, &database.Tag{ - Name: "tag_" + uuid.NewString(), - Category: "task", - Group: "", - Scope: database.ModelTagScope, - BuiltIn: true, - ShowName: "tag one", - }) - err = ts.SaveTags(ctx, newTags) + modelTag, err := ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", database.ModelTagScope) + require.Empty(t, err) + datasetTag, err := ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", database.DatasetTagScope) + require.Empty(t, err) + codeTag, err := ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", database.CodeTagScope) + require.Empty(t, err) + promptTag, err := ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", database.PromptTagScope) + require.Empty(t, err) + spaceTag, err := ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", database.SpaceTagScope) require.Empty(t, err) tags, err = ts.AllTags(ctx) require.Empty(t, err) - require.Equal(t, 2, len(tags)) + require.Equal(t, 5, len(tags)) + + modelTags, err := ts.AllModelTags(ctx) + require.Empty(t, err) + require.Equal(t, 1, len(modelTags)) + require.Equal(t, modelTag.Name, modelTags[0].Name) + + datasetTags, err := ts.AllDatasetTags(ctx) + require.Empty(t, err) + require.Equal(t, 1, len(datasetTags)) + require.Equal(t, datasetTag.Name, datasetTags[0].Name) + + codeTags, err := ts.AllCodeTags(ctx) + require.Empty(t, err) + require.Equal(t, 1, len(codeTags)) + require.Equal(t, codeTag.Name, codeTags[0].Name) + + promptTags, err := ts.AllPromptTags(ctx) + require.Empty(t, err) + require.Equal(t, 1, len(promptTags)) + require.Equal(t, promptTag.Name, promptTags[0].Name) + + spaceTags, err := ts.AllSpaceTags(ctx) + require.Empty(t, err) + require.Equal(t, 1, len(spaceTags)) + require.Equal(t, spaceTag.Name, spaceTags[0].Name) } // TestAllTagsByScope tests the AllTagsByScope method @@ -145,151 +160,6 @@ func TestTagStore_GetTagsByScopeAndCategories(t *testing.T) { require.Len(t, tags, 2) } -// TestAllModelTags tests the AllModelTags method -func TestTagStore_AllModelTags(t *testing.T) { - db := tests.InitTestDB() - defer db.Close() - - ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) - defer cancel() - - var err error - //clear all existing data - _, err = db.Core.NewDelete().Model(&database.Tag{}).Where("1=1").Exec(ctx) - require.Empty(t, err) - - ts := database.NewTagStoreWithDB(db) - tags, err := ts.AllModelTags(ctx) - require.Empty(t, err) - require.Len(t, tags, 0) - - _, err = ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", database.ModelTagScope) - require.Empty(t, err) - _, err = ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", database.DatasetTagScope) - require.Empty(t, err) - - tags, err = ts.AllModelTags(ctx) - require.Empty(t, err) - require.Len(t, tags, 1) - -} - -// TestAllPromptTags tests the AllPromptTags method -func TestTagStore_AllPromptTags(t *testing.T) { - db := tests.InitTestDB() - defer db.Close() - - ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) - defer cancel() - - var err error - //clear all existing data - _, err = db.Core.NewDelete().Model(&database.Tag{}).Where("1=1").Exec(ctx) - require.Empty(t, err) - - ts := database.NewTagStoreWithDB(db) - tags, err := ts.AllPromptTags(ctx) - require.Empty(t, err) - require.Len(t, tags, 0) - - _, err = ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", database.PromptTagScope) - require.Empty(t, err) - _, err = ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", database.DatasetTagScope) - require.Empty(t, err) - - tags, err = ts.AllPromptTags(ctx) - require.Empty(t, err) - require.Len(t, tags, 1) - -} - -// TestAllDatasetTags tests the AllDatasetTags method -func TestTagStore_AllDatasetTags(t *testing.T) { - db := tests.InitTestDB() - defer db.Close() - - ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) - defer cancel() - - var err error - //clear all existing data - _, err = db.Core.NewDelete().Model(&database.Tag{}).Where("1=1").Exec(ctx) - require.Empty(t, err) - - ts := database.NewTagStoreWithDB(db) - tags, err := ts.AllDatasetTags(ctx) - require.Empty(t, err) - require.Len(t, tags, 0) - - _, err = ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", database.PromptTagScope) - require.Empty(t, err) - _, err = ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", database.DatasetTagScope) - require.Empty(t, err) - - tags, err = ts.AllDatasetTags(ctx) - require.Empty(t, err) - require.Len(t, tags, 1) - -} - -// TestAllCodeTags tests the AllCodeTags method -func TestTagStore_AllCodeTags(t *testing.T) { - db := tests.InitTestDB() - defer db.Close() - - ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) - defer cancel() - - var err error - //clear all existing data - _, err = db.Core.NewDelete().Model(&database.Tag{}).Where("1=1").Exec(ctx) - require.Empty(t, err) - - ts := database.NewTagStoreWithDB(db) - tags, err := ts.AllCodeTags(ctx) - require.Empty(t, err) - require.Len(t, tags, 0) - - _, err = ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", database.CodeTagScope) - require.Empty(t, err) - _, err = ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", database.DatasetTagScope) - require.Empty(t, err) - - tags, err = ts.AllCodeTags(ctx) - require.Empty(t, err) - require.Len(t, tags, 1) - -} - -// TestAllSpaceTags tests the AllSpaceTags method -func TestTagStore_AllSpaceTags(t *testing.T) { - db := tests.InitTestDB() - defer db.Close() - - ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second) - defer cancel() - - var err error - //clear all existing data - _, err = db.Core.NewDelete().Model(&database.Tag{}).Where("1=1").Exec(ctx) - require.Empty(t, err) - - ts := database.NewTagStoreWithDB(db) - tags, err := ts.AllSpaceTags(ctx) - require.Empty(t, err) - require.Len(t, tags, 0) - - _, err = ts.CreateTag(ctx, "task", "tag_"+uuid.New().String(), "Group One", database.SpaceTagScope) - require.Empty(t, err) - _, err = ts.CreateTag(ctx, "library", "tag_"+uuid.New().String(), "Group One", database.DatasetTagScope) - require.Empty(t, err) - - tags, err = ts.AllSpaceTags(ctx) - require.Empty(t, err) - require.Len(t, tags, 1) - -} - // TestAllModelCategories tests the AllModelCategories method func TestTagStore_AllModelCategories(t *testing.T) { db := tests.InitTestDB() From cd87209c9688da04a964ffa9deb4afbd72ce699b Mon Sep 17 00:00:00 2001 From: Lei Da Date: Thu, 21 Nov 2024 14:43:30 +0800 Subject: [PATCH 4/4] fix lint errors --- builder/store/database/tag.go | 2 -- builder/store/database/tag_test.go | 7 ++++--- 2 files changed, 4 insertions(+), 5 deletions(-) diff --git a/builder/store/database/tag.go b/builder/store/database/tag.go index 9e51a241..3c0b03fa 100644 --- a/builder/store/database/tag.go +++ b/builder/store/database/tag.go @@ -63,8 +63,6 @@ const ( PromptTagScope TagScope = "prompt" ) -const defaultTagGroup = "" - type Tag struct { ID int64 `bun:",pk,autoincrement" json:"id"` Name string `bun:",notnull" json:"name" yaml:"name"` diff --git a/builder/store/database/tag_test.go b/builder/store/database/tag_test.go index e60113bb..777b4f4c 100644 --- a/builder/store/database/tag_test.go +++ b/builder/store/database/tag_test.go @@ -398,12 +398,12 @@ func TestTagStore_SetMetaTags(t *testing.T) { BuiltIn: true, ShowName: "", }) - repoTags, err := ts.SetMetaTags(ctx, types.ModelRepo, userName, repoName, tags) + _, err = ts.SetMetaTags(ctx, types.ModelRepo, userName, repoName, tags) // should report err as framework tag is not allowed require.NotEmpty(t, err) tags = tags[:1] - repoTags, err = ts.SetMetaTags(ctx, types.ModelRepo, userName, repoName, tags) + repoTags, err := ts.SetMetaTags(ctx, types.ModelRepo, userName, repoName, tags) require.Empty(t, err) require.Len(t, repoTags, 1) } @@ -528,7 +528,8 @@ func TestTagStore_RemoveRepoTags(t *testing.T) { require.Empty(t, err) require.NotNil(t, repo) // set repo tags - ts.UpsertRepoTags(ctx, repo.ID, []int64{}, []int64{tag1.ID, tag2.ID}) + err = ts.UpsertRepoTags(ctx, repo.ID, []int64{}, []int64{tag1.ID, tag2.ID}) + require.Empty(t, err) removeTagIds := make([]int64, 0, 1) removeTagIds = append(removeTagIds, tag2.ID)