package commands

import (
	"strings"
)

func ParseCommand(s string) *Command {
	if s == "" {
		return nil
	}

	startIndex := 0
	for i := range len(s) {
		if s[i] >= 32 && s[i] <= 126 {
			startIndex = i

			break
		}
	}
	if startIndex > 0 {
		s = s[startIndex:]
	}

	parts := strings.Split(s, " ")
	if len(parts) == 0 {
		return nil
	}

	cmd := &Command{
		Params: make(map[string]string),
	}

	// TS3 list responses (clientlist, channellist) arrive as nameless rows of
	// key=value pairs. Only treat the first token as a command name when it is
	// NOT a key=value pair; otherwise every token is a parameter.
	start := 0
	if !strings.Contains(parts[0], "=") {
		cmd.Name = parts[0]
		start = 1
	}

	for _, p := range parts[start:] {
		if p == "" {
			continue
		}
		kv := strings.SplitN(p, "=", 2)
		if len(kv) == 2 {
			cmd.Params[Unescape(kv[0])] = Unescape(kv[1])
		} else {
			cmd.Params[Unescape(p)] = ""
		}
	}

	return cmd
}

var unescaper = strings.NewReplacer(
	"\\\\", "\\",
	"\\/", "/",
	"\\s", " ",
	"\\p", "|",
	"\\a", "\a",
	"\\b", "\b",
	"\\f", "\f",
	"\\n", "\n",
	"\\r", "\r",
	"\\t", "\t",
	"\\v", "\v",
)

func Unescape(s string) string {
	return unescaper.Replace(s)
}
