package org

import (
	"context"
	"fmt"
	"regexp"
	"strings"

	"go.b0esche.cloud/backend/internal/database"

	"github.com/google/uuid"
	"github.com/jackc/pgconn"
)

// ResolveUserOrgs returns the organizations a user belongs to
func ResolveUserOrgs(ctx context.Context, db *database.DB, userID uuid.UUID) ([]database.Organization, error) {
	return db.GetUserOrganizations(ctx, userID)
}

// CheckMembership checks if user is member of org and returns role
func CheckMembership(ctx context.Context, db *database.DB, userID, orgID uuid.UUID) (string, error) {
	membership, err := db.GetUserMembership(ctx, userID, orgID)
	if err != nil {
		return "", err
	}
	return membership.Role, nil
}

// CreateOrg creates a new organization and adds the user as owner
func CreateOrg(ctx context.Context, db *database.DB, userID uuid.UUID, name, slug string) (*database.Organization, error) {
	trimmedName := strings.TrimSpace(name)
	if trimmedName == "" {
		return nil, fmt.Errorf("organization name cannot be empty")
	}

	baseSlug := slugify(slug)
	if baseSlug == "" {
		baseSlug = slugify(trimmedName)
	}
	if baseSlug == "" {
		baseSlug = fmt.Sprintf("org-%s", uuid.NewString()[:8])
	}

	var org *database.Organization
	var err error
	// Try a handful of suffixes on unique constraint violation
	for i := 0; i < 5; i++ {
		candidate := baseSlug
		if i > 0 {
			candidate = fmt.Sprintf("%s-%d", baseSlug, i+1)
		}
		org, err = db.CreateOrg(ctx, userID, trimmedName, candidate)
		if err != nil {
			if pgErr, ok := err.(*pgconn.PgError); ok && pgErr.Code == "23505" {
				// Unique violation; try next suffix
				continue
			}
			return nil, err
		}
		break
	}
	if err != nil {
		return nil, err
	}

	if err = db.AddMembership(ctx, userID, org.ID, "owner"); err != nil {
		return nil, err
	}
	return org, nil
}

// slugify converts a string to a URL-safe slug with hyphens.
func slugify(s string) string {
	lower := strings.ToLower(strings.TrimSpace(s))
	if lower == "" {
		return ""
	}
	// Replace non-alphanumeric with hyphen
	re := regexp.MustCompile(`[^a-z0-9]+`)
	slug := re.ReplaceAllString(lower, "-")
	slug = strings.Trim(slug, "-")
	// Collapse multiple hyphens
	slug = strings.ReplaceAll(slug, "--", "-")
	return slug
}
