package compute

import (
	"context"
	"net/http"

	"repository.basistech.ru/BASIS/decort-golang-sdk/internal/constants"
	"repository.basistech.ru/BASIS/decort-golang-sdk/internal/validators"
)

// CloneRequest struct to clone compute instance
type CloneRequest struct {
	// ID of compute instance
	// Required: true
	ComputeID uint64 `url:"computeId" json:"computeId" validate:"required"`

	// Name of the clone
	// Required: true
	Name string `url:"name" json:"name" validate:"required"`

	// ID of the Storage Policy
	// Required: true
	StoragePolicyID uint64 `url:"storage_policy_id" json:"storage_policy_id" validate:"required"`

	// Timestamp of the parent's snapshot to create clone from
	// Required: false
	SnapshotTimestamp uint64 `url:"snapshotTimestamp,omitempty" json:"snapshotTimestamp,omitempty"`

	// Name of the parent's snapshot to create clone from
	// Required: false
	SnapshotName string `url:"snapshotName,omitempty" json:"snapshotName,omitempty"`

	// true ignore that the compute is running
	// Default: false
	// Required: false
	Force bool `url:"force" json:"force"`

	// The name of the pool to migrate disks to
	// Required: false
	PoolName string `url:"pool_name" json:"pool_name"`

	// The ID of the SEP to migrate disks to
	// Required: false
	SEPID uint64 `url:"sep_id" json:"sep_id"`
}

type wrapperCloneRequest struct {
	CloneRequest

	AsyncMode bool `url:"asyncMode" json:"asyncMode"`
}

// Clone clones compute instance
func (c Compute) Clone(ctx context.Context, req CloneRequest) (string, error) {
	err := validators.ValidateRequest(req)
	if err != nil {
		return "", validators.ValidationErrors(validators.GetErrors(err))
	}

	reqWrapped := wrapperCloneRequest{
		CloneRequest: req,
		AsyncMode:    false,
	}

	url := "/cloudapi/compute/clone"

	res, err := c.client.DecortApiCallCtype(ctx, http.MethodPost, url, constants.MIMEJSON, reqWrapped)
	if err != nil {
		return "", err
	}

	return string(res), nil
}

// CloneAsync clones compute instance with AsyncMode
func (c Compute) CloneAsync(ctx context.Context, req CloneRequest) (string, error) {
	err := validators.ValidateRequest(req)
	if err != nil {
		return "", validators.ValidationErrors(validators.GetErrors(err))
	}

	reqWrapped := wrapperCloneRequest{
		CloneRequest: req,
		AsyncMode:    true,
	}

	url := "/cloudapi/compute/clone"

	res, err := c.client.DecortApiCallCtype(ctx, http.MethodPost, url, constants.MIMEJSON, reqWrapped)
	if err != nil {
		return "", err
	}

	return string(res), nil
}
