- Reorganized models by replacing the assistant and chat models with a new agent structure, including assistant, chat, and history models. - Updated user model relationships to reflect changes in role and type references, ensuring consistency with the new model structure. - Removed obsolete organization and user role models, streamlining the overall architecture. - Adjusted system model mappings to incorporate new member and role models, enhancing clarity in user management.
219 lines
7.2 KiB
Go
219 lines
7.2 KiB
Go
package user_test
|
|
|
|
import (
|
|
"context"
|
|
"testing"
|
|
|
|
"github.com/stretchr/testify/require"
|
|
"github.com/yaoapp/gou/model"
|
|
"github.com/yaoapp/kun/maps"
|
|
"github.com/yaoapp/yao/config"
|
|
"github.com/yaoapp/yao/openapi/oauth/providers/user"
|
|
"github.com/yaoapp/yao/test"
|
|
)
|
|
|
|
// TestUserData represents test user data structure (without UserID - auto-generated)
|
|
type TestUserData struct {
|
|
PreferredUsername string `json:"preferred_username"`
|
|
Email string `json:"email"`
|
|
Password string `json:"password"`
|
|
Name string `json:"name"`
|
|
GivenName string `json:"given_name"`
|
|
FamilyName string `json:"family_name"`
|
|
Status string `json:"status"`
|
|
RoleID string `json:"role_id"`
|
|
TypeID string `json:"type_id"`
|
|
EmailVerified bool `json:"email_verified"`
|
|
Metadata map[string]interface{} `json:"metadata"`
|
|
}
|
|
|
|
var (
|
|
testProvider *user.DefaultUser
|
|
)
|
|
|
|
// prepare initializes the test environment for each test function.
|
|
//
|
|
// PREREQUISITES:
|
|
// Before running any tests in this package, you MUST execute the following command in your terminal:
|
|
//
|
|
// source $YAO_SOURCE_ROOT/env.local.sh
|
|
//
|
|
// This loads the required environment variables for the test environment.
|
|
//
|
|
// WHAT THIS FUNCTION DOES:
|
|
// Step 1: Calls test.Prepare(t, config.Conf) to initialize the base Yao test environment
|
|
//
|
|
// This sets up database connections, configurations, and other core dependencies
|
|
//
|
|
// Step 2: Creates test provider with configured options
|
|
//
|
|
// This sets up the DefaultUser provider for testing with test-specific configuration
|
|
//
|
|
// Usage pattern for ALL user provider tests:
|
|
//
|
|
// func TestYourFunction(t *testing.T) {
|
|
// prepare(t)
|
|
// defer clean()
|
|
//
|
|
// ctx := context.Background() // Each test creates its own context
|
|
//
|
|
// // Your actual test code here...
|
|
// }
|
|
func prepare(t *testing.T) {
|
|
// Step 1: Initialize base test environment with all Yao dependencies
|
|
test.Prepare(t, config.Conf)
|
|
|
|
// Step 2: Initialize test provider
|
|
testProvider = user.NewDefaultUser(&user.DefaultUserOptions{
|
|
Prefix: "test:",
|
|
IDStrategy: user.NanoIDStrategy,
|
|
IDPrefix: "test_",
|
|
})
|
|
}
|
|
|
|
// clean cleans up the test environment after each test function.
|
|
//
|
|
// WHAT THIS FUNCTION DOES:
|
|
// Step 1: Clean up test data from database
|
|
// Step 2: Reset global variables
|
|
// Step 3: Call test.Clean() to clean up the base test environment
|
|
//
|
|
// This function should ALWAYS be called with defer to ensure cleanup happens even if tests panic.
|
|
func clean() {
|
|
// Step 1: Clean up test data
|
|
cleanupTestData()
|
|
|
|
// Step 2: Reset global variables
|
|
testProvider = nil
|
|
|
|
// Step 3: Clean up base test environment
|
|
test.Clean()
|
|
}
|
|
|
|
// cleanupTestData removes all test data
|
|
func cleanupTestData() {
|
|
if testProvider == nil {
|
|
return
|
|
}
|
|
|
|
// Use DestroyWhere (hard delete) to avoid soft delete complications
|
|
// Clean OAuth accounts first (due to foreign key constraints)
|
|
oauthModel := model.Select("__yao.user.oauth_account")
|
|
oauthPatterns := []string{
|
|
"%oauth_test%", "%_list_%", "%oauthlist%", "%oautherror%",
|
|
"%google_%", "%github_%", "%apple_%", "%_delete_%",
|
|
"%discord_%", "%linkedin_%", "%twitter_%",
|
|
}
|
|
for _, pattern := range oauthPatterns {
|
|
oauthModel.DestroyWhere(model.QueryParam{
|
|
Wheres: []model.QueryWhere{
|
|
{Column: "sub", OP: "like", Value: pattern},
|
|
},
|
|
})
|
|
}
|
|
|
|
// Clean roles (should be done before users due to potential role_id references)
|
|
roleModel := model.Select("__yao.role")
|
|
rolePatterns := []string{
|
|
"test%", "%testrole%", "%listrole%", "%permrole%", "%adminrole%", "%userrole%",
|
|
"%inactiverole%", "%systemrole%", "%validrole%", "%emptyupdate%", "%emptyperm%",
|
|
"%guestrole%", "%scoperole%", "%test-role-for-exists%",
|
|
}
|
|
for _, pattern := range rolePatterns {
|
|
roleModel.DestroyWhere(model.QueryParam{
|
|
Wheres: []model.QueryWhere{
|
|
{Column: "role_id", OP: "like", Value: pattern},
|
|
},
|
|
})
|
|
}
|
|
|
|
// Clean types (should be done before users due to potential type_id references)
|
|
typeModel := model.Select("__yao.user.type")
|
|
typePatterns := []string{
|
|
"test%", "%testtype%", "%listtype%", "%configtype%", "%basictype%", "%premiumtype%",
|
|
"%inactivetype%", "%validtype%", "%emptyupdate%", "%emptyconfig%", "%scopetype%",
|
|
"%opentype%", "%test-type-for-exists%",
|
|
}
|
|
for _, pattern := range typePatterns {
|
|
typeModel.DestroyWhere(model.QueryParam{
|
|
Wheres: []model.QueryWhere{
|
|
{Column: "type_id", OP: "like", Value: pattern},
|
|
},
|
|
})
|
|
}
|
|
|
|
// Clean users
|
|
userModel := model.Select("__yao.user")
|
|
|
|
// Delete test users by pattern (using hard delete)
|
|
userPatterns := []string{
|
|
"test-%", "test_%", "%testuser%", "%oauthtest%", "%oauthlist%",
|
|
"%oautherror%", "%deletetest%", "%roleuser%", "%typeuser%", "%scopeuser%",
|
|
"%erroruser%", "%noroleuser%", "%clearnouser%", "%integuser%", "%notypeuser%",
|
|
"%openuser%", "%clearnotypeuser%", "%test-user-for-exists%", "%perf-test-user%",
|
|
}
|
|
for _, pattern := range userPatterns {
|
|
userModel.DestroyWhere(model.QueryParam{
|
|
Wheres: []model.QueryWhere{
|
|
{Column: "user_id", OP: "like", Value: pattern},
|
|
},
|
|
})
|
|
}
|
|
|
|
// Also clean by username pattern
|
|
usernamePatterns := []string{
|
|
"testuser%", "%oauth_%", "%deletetest%", "%roleuser%", "%typeuser%",
|
|
"%scopeuser%", "%erroruser%", "%noroleuser%", "%clearnouser%", "%integuser%",
|
|
"%notypeuser%", "%openuser%", "%clearnotypeuser%", "%testexistsuser%", "%perfuser%",
|
|
}
|
|
for _, pattern := range usernamePatterns {
|
|
userModel.DestroyWhere(model.QueryParam{
|
|
Wheres: []model.QueryWhere{
|
|
{Column: "preferred_username", OP: "like", Value: pattern},
|
|
},
|
|
})
|
|
}
|
|
}
|
|
|
|
// setupTestUser creates a user in database for testing
|
|
func setupTestUser(t *testing.T, ctx context.Context, userData *TestUserData) (interface{}, string) {
|
|
userMap := maps.MapStrAny{
|
|
// user_id will be auto-generated by CreateUser
|
|
"preferred_username": userData.PreferredUsername,
|
|
"email": userData.Email,
|
|
"password": userData.Password, // Will be auto-hashed by Yao
|
|
"name": userData.Name,
|
|
"given_name": userData.GivenName,
|
|
"family_name": userData.FamilyName,
|
|
"status": userData.Status,
|
|
"role_id": userData.RoleID,
|
|
"type_id": userData.TypeID,
|
|
"email_verified": userData.EmailVerified,
|
|
"metadata": userData.Metadata,
|
|
}
|
|
|
|
id, err := testProvider.CreateUser(ctx, userMap)
|
|
require.NoError(t, err)
|
|
|
|
// Return both database ID and auto-generated user_id
|
|
userID := userMap["user_id"].(string)
|
|
return id, userID
|
|
}
|
|
|
|
// createTestUserData creates test user data with unique identifier
|
|
func createTestUserData(id string) *TestUserData {
|
|
return &TestUserData{
|
|
// user_id will be auto-generated, not set here
|
|
PreferredUsername: "testuser" + id,
|
|
Email: "testuser" + id + "@example.com",
|
|
Password: "TestPass" + id + "!",
|
|
Name: "Test User " + id,
|
|
GivenName: "Test",
|
|
FamilyName: "User " + id,
|
|
Status: "active",
|
|
RoleID: "user",
|
|
TypeID: "regular",
|
|
EmailVerified: true,
|
|
Metadata: map[string]interface{}{"source": "test", "id": id},
|
|
}
|
|
}
|