package host

import (
	"fmt"
	"net/url"

	"github.com/pingcap/errors"
	"github.com/pingcap/log"
	"github.com/pingcap/test-infra/sdk/resource"
)

type LoaderOpts struct {
	DataDir string `json:"data-dir"`
	Threads int    `json:"threads"`
	Timeout string `json:"timeout"`
	SQLMode string `json:"sql-mode"`
}

type LoaderFullOpts struct {
	*LoaderOpts
	mysqlUrl *url.URL
}

func (l *LoaderFullOpts) Command() string {
	cmd := fmt.Sprintf("/loader -d \"%s\"", l.DataDir)
	if l.Threads != 0 {
		cmd += fmt.Sprintf(" -t %d", l.Threads)
	}
	if l.SQLMode != "" {
		cmd += fmt.Sprintf(" -m '%s'", l.SQLMode)
	}
	return cmd + " " + NewMySQLOpts(l.mysqlUrl).Opts()
}

func NewLoaderFullOpts(loaderOpts *LoaderOpts, mysqlUrl *url.URL) *LoaderFullOpts {
	return &LoaderFullOpts{
		loaderOpts,
		mysqlUrl,
	}
}

type LoaderHost struct{ Host }

func NewLoaderHost(res resource.WorkloadNode) *LoaderHost {
	return &LoaderHost{Host{res}}
}

func (l *LoaderHost) Import(mysqlUrl *url.URL, opts *LoaderOpts) error {
	output, err := l.ExecCmd(NewLoaderFullOpts(opts, mysqlUrl).Command(), opts.Timeout)
	if err != nil {
		return errors.Trace(err)
	}
	if output.ExitCode != 0 {
		log.Info("Loader failed")
		return errors.New("Loader failed")
	}
	return nil
}
