package externaladmin import ( "context" "errors" "net/http" "net/http/httptest" "testing" adminmiddleware "hyapp-admin-server/internal/middleware" "hyapp-admin-server/internal/model" "github.com/DATA-DOG/go-sqlmock" "github.com/gin-gonic/gin" "google.golang.org/grpc" "gorm.io/driver/mysql" "gorm.io/gorm" userv1 "hyapp.local/api/proto/user/v1" ) type managerTeamHostClient struct { userv1.UserHostServiceClient request *userv1.ListManagerTeamAgenciesRequest calls int } func (client *managerTeamHostClient) ListManagerTeamAgencies(_ context.Context, request *userv1.ListManagerTeamAgenciesRequest, _ ...grpc.CallOption) (*userv1.ListManagerTeamAgenciesResponse, error) { client.calls++ client.request = request return &userv1.ListManagerTeamAgenciesResponse{ Agencies: []*userv1.ManagerTeamAgency{ {AgencyId: 101, OwnerUserId: 1001, ParentBdUserId: 2001}, {AgencyId: 102, OwnerUserId: 1002, ParentBdUserId: 2002}, {AgencyId: 103, OwnerUserId: 1003, ParentBdUserId: 2003}, }, TotalBdLeaders: 4, TotalBds: 9, Truncated: true, }, nil } func TestRetiredMyTeamRouteIsNotExposed(t *testing.T) { gin.SetMode(gin.TestMode) client := &managerTeamHostClient{} handler := New(nil, nil, Config{}, nil, WithUserHostClient(client)) engine := gin.New() group := engine.Group("/api/v1/external") group.Use(func(c *gin.Context) { c.Set(contextPrincipal, SessionPrincipal{AppCode: "fami", LinkedAppUserID: 42}) c.Set(adminmiddleware.ContextPermissions, []string{"agency:list"}) c.Next() }) registerBusinessWhitelist(group, handler, BusinessHandlers{}) request := httptest.NewRequest(http.MethodGet, "/api/v1/external/admin/my-team/agencies?page=2&page_size=2&manager_user_id=999&user_id=888", nil) responseRecorder := httptest.NewRecorder() engine.ServeHTTP(responseRecorder, request) if responseRecorder.Code != http.StatusNotFound { t.Fatalf("status = %d body=%s", responseRecorder.Code, responseRecorder.Body.String()) } if client.calls != 0 { t.Fatalf("retired route called owner service %d times", client.calls) } } func TestValidateParentRejectsManagerWhoseLocalMovedRegion(t *testing.T) { adminSQL, adminMock, err := sqlmock.New() if err != nil { t.Fatalf("new admin sqlmock: %v", err) } defer adminSQL.Close() adminDB, err := gorm.Open(mysql.New(mysql.Config{Conn: adminSQL, SkipInitializeWithVersion: true}), &gorm.Config{}) if err != nil { t.Fatalf("open admin gorm: %v", err) } userDB, userMock, err := sqlmock.New() if err != nil { t.Fatalf("new user sqlmock: %v", err) } defer userDB.Close() managerID := uint64(11) localID := uint64(9) accountColumns := []string{"id", "app_code", "linked_app_user_id", "identity_type", "parent_account_id", "status"} adminMock.ExpectQuery("SELECT \\* FROM `external_admin_accounts` WHERE id = \\? AND app_code = \\? AND identity_type = \\? AND status = \\?"). WithArgs(managerID, "fami", model.ExternalAdminIdentityCountryManager, model.ExternalAdminStatusActive, 1). WillReturnRows(sqlmock.NewRows(accountColumns).AddRow( managerID, "fami", int64(1100), model.ExternalAdminIdentityCountryManager, localID, model.ExternalAdminStatusActive, )) userMock.ExpectQuery("SELECT u.region_id"). WithArgs("fami", int64(1100)). WillReturnRows(sqlmock.NewRows([]string{"region_id"}).AddRow(int64(12))) adminMock.ExpectQuery("SELECT \\* FROM `external_admin_accounts` WHERE id = \\? AND app_code = \\? AND identity_type = \\? AND status = \\?"). WithArgs(localID, "fami", model.ExternalAdminIdentityLocal, model.ExternalAdminStatusActive, 1). WillReturnRows(sqlmock.NewRows(accountColumns).AddRow( localID, "fami", int64(900), model.ExternalAdminIdentityLocal, nil, model.ExternalAdminStatusActive, )) userMock.ExpectQuery("SELECT u.region_id"). WithArgs("fami", int64(900)). WillReturnRows(sqlmock.NewRows([]string{"region_id"}).AddRow(int64(13))) service := NewService(adminDB, userDB, Config{}) if _, err := service.validateParentForChild( t.Context(), adminDB, "fami", model.ExternalAdminIdentityExternalSuperAdmin, &managerID, 12, ); !errors.Is(err, ErrInvalidHierarchy) { t.Fatalf("validate parent error = %v, want ErrInvalidHierarchy", err) } if err := adminMock.ExpectationsWereMet(); err != nil { t.Fatalf("admin expectations: %v", err) } if err := userMock.ExpectationsWereMet(); err != nil { t.Fatalf("user expectations: %v", err) } }