package service_test

import (
	"context"
	"testing"
	"time"

	"github.com/pingcap/agent-git-service/internal/db"
	"github.com/pingcap/agent-git-service/internal/service"
	"github.com/pingcap/agent-git-service/internal/testharness"
)

// setupTestService builds a bare service backed by TiDB + temp gitstore.
// Thin wrapper over testharness.NewService. Every caller receives the fixture's
// explicit tenant capability; service tests never rely on a default tenant.
func setupTestService(t testing.TB) (*service.Service, *testharness.TenantHandle, func()) {
	return testharness.NewService(t, testharness.ServiceConfig{})
}

func setupTestServiceWithConfig(t testing.TB, cfg testharness.ServiceConfig) (*service.Service, *testharness.TenantHandle, func()) {
	return testharness.NewService(t, cfg)
}

func setupExecutableWorkflowTestService(t testing.TB, timeout time.Duration) (*service.Service, *testharness.TenantHandle, func()) {
	return testharness.NewService(t, testharness.ServiceConfig{
		Workflow: service.WorkflowPolicy{
			Enabled: true,
			Timeout: timeout,
		},
	})
}

func testContextWithUser(ctx context.Context, user db.User) context.Context {
	ctx, err := service.ContextWithUserForTest(ctx, user)
	if err != nil {
		panic(err)
	}
	return ctx
}

func mustAddOrgMember(t testing.TB, svc *service.Service, ctx context.Context, orgID, userID uint, role string) {
	t.Helper()
	if err := svc.AddOrgMember(ctx, orgID, userID, role); err != nil {
		t.Fatalf("AddOrgMember(%d,%d,%s): %v", orgID, userID, role, err)
	}
}

// setupRepoForTest creates a user and repo for use in service tests.
func setupRepoForTest(t testing.TB, svc *service.Service, ctx context.Context, login, repoName string) {
	t.Helper()
	svc.DBForCtx(ctx).Create(&db.User{Login: login, Name: login, Type: db.TypeUser})
	_, err := svc.CreateRepo(ctx, service.CreateRepoInput{OwnerLogin: login, Name: repoName})
	if err != nil {
		t.Fatalf("setupRepoForTest failed: %v", err)
	}
}

func testWorkflowRunJob(runID uint, name string) db.WorkflowRunJob {
	now := time.Now()
	return db.WorkflowRunJob{
		RunID:       runID,
		Name:        name,
		Status:      db.RunCompleted,
		Conclusion:  db.ConclusionSuccess,
		StartedAt:   now,
		CompletedAt: now,
	}
}

func testActionCache(repoID uint, key, ref, version string) db.ActionCache {
	return db.ActionCache{
		RepositoryID:   repoID,
		Key:            key,
		Ref:            ref,
		Version:        version,
		LastAccessedAt: time.Now(),
	}
}
