package controller

import (
	"context"
	"errors"
	"fmt"
	"log"
	"ticket-pimp/internal/domain"
	"ticket-pimp/internal/storage/db"
	"time"

	"github.com/jackc/pgx/v5/pgtype"
)

type GitRequest struct {
	ChannelID    string
	InsertedName string
	IsBuildGit   bool
}

func (wc *WorkflowController) createGitForExistingProject(ctx context.Context, req GitRequest, p *domain.Project) *ProjectResponse {
	var (
		name     string = ""
		dbticket db.Ticket
	)
	switch {
	case p.Key != "":
		name = p.Key
		if req.IsBuildGit {
			name += "-build"
		}
	case req.InsertedName != "":
		name = req.InsertedName
		if req.IsBuildGit {
			name += "-build"
		}
	}

	// response := wc.ICloud.CreateFolder(name)
	git, err := wc.IGit.CreateRepo(name)
	if err != nil {
		return &ProjectResponse{
			Project: p,
			Message: fmt.Errorf("unable to create git w/ an error: %v", err),
		}
	}

	if req.IsBuildGit {
		dbticket, err = wc.q.UpdateTicketBuildGit(
			ctx,
			db.UpdateTicketBuildGitParams{
				BuildGit:  pgtype.Text{String: git.HtmlUrl, Valid: true},
				UpdatedAt: pgtype.Timestamptz{Time: time.Now(), InfinityModifier: 0, Valid: true},
				Channelid: pgtype.Text{String: req.ChannelID, Valid: true},
			})
		if err != nil {
			log.Printf("unable to scan row from db: %v", err)
			return &ProjectResponse{
				Project: p,
				Message: fmt.Errorf("unable to update project: %v", err),
			}
		}
	} else {
		dbticket, err = wc.q.UpdateTicketProjectGit(
			ctx,
			db.UpdateTicketProjectGitParams{
				ProjectGit: pgtype.Text{String: git.HtmlUrl, Valid: true},
				UpdatedAt:  pgtype.Timestamptz{Time: time.Now(), InfinityModifier: 0, Valid: true},
				Channelid:  pgtype.Text{String: req.ChannelID, Valid: true},
			},
		)
		if err != nil {
			log.Printf("unable to scan row from db: %v", err)
			return &ProjectResponse{
				Project: p,
				Message: fmt.Errorf("unable to update project: %v", err),
			}
		}
	}

	return &ProjectResponse{
		Project: &domain.Project{
			ID:         string(dbticket.ID),
			Name:       dbticket.Title.String,
			Key:        dbticket.Key.String,
			ChannelID:  dbticket.Channelid.String,
			ProjectGit: dbticket.ProjectGit.String,
			BuildGit:   dbticket.BuildGit.String,
			Folder:     dbticket.Folder.String,
		},
		Message: err,
	}
}

func (wc *WorkflowController) CreateGit(ctx context.Context, req GitRequest) *ProjectResponse {

	var p *domain.Project = nil

	if req.ChannelID != "" {
		projectFromDB, err := wc.GetProjectByChannelID(ctx, req.ChannelID)
		if err != nil {
			return &ProjectResponse{
				Project: nil,
				Message: fmt.Errorf("unable to retrieve project from db: %v", err),
			}
		}
		p = projectFromDB
	}

	switch {
	case p != nil && req.IsBuildGit:
		if p.BuildGit != "" {
			return &ProjectResponse{
				Project: p,
				Message: errors.New("build git already exists"),
			}
		} else {
			return wc.createGitForExistingProject(ctx, req, p)
		}
	case p != nil && !req.IsBuildGit:
		if p.ProjectGit != "" {
			return &ProjectResponse{
				Project: p,
				Message: errors.New("project git already exists"),
			}
		} else {
			return wc.createGitForExistingProject(ctx, req, p)
		}
	default:
		if req.InsertedName != "" {

			if req.IsBuildGit {
				req.InsertedName += "-build"
			}

			git, err := wc.IGit.CreateRepo(req.InsertedName)
			if err != nil || git == nil {
				return &ProjectResponse{
					Project: nil,
					Message: err,
				}
			} else {
				if req.IsBuildGit {
					return &ProjectResponse{
						Project: &domain.Project{
							BuildGit: git.HtmlUrl,
						},
						Message: err,
					}
				}
				return &ProjectResponse{
					Project: &domain.Project{
						ProjectGit: git.HtmlUrl,
					},
					Message: err,
				}
			}
		} else {
			return &ProjectResponse{
				Project: nil,
				Message: errors.New("передано пустое имя"),
			}
		}
	}
}
