// Copyright 2015 The Vanadium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

// The following enables go generate to generate the doc.go file.
//go:generate go run $JIRI_ROOT/release/go/src/v.io/x/lib/cmdline/testdata/gendoc.go . -help

package main

import (
	"errors"
	"fmt"
	"sort"
	"strings"
	"sync"
	"time"

	"v.io/v23"
	"v.io/v23/context"
	"v.io/v23/naming"
	"v.io/v23/rpc"
	"v.io/v23/security"
	"v.io/v23/vtrace"
	"v.io/x/lib/cmdline"
	"v.io/x/ref/examples/rps"
	"v.io/x/ref/examples/rps/internal"
	"v.io/x/ref/internal/logger"
	"v.io/x/ref/lib/v23cmd"
	_ "v.io/x/ref/runtime/factories/roaming"
)

var name, aclFile, mountPrefix string

func main() {
	cmdRoot.Flags.StringVar(&name, "name", "", "Identifier to publish as (defaults to principal's blessing names).")
	cmdRoot.Flags.StringVar(&aclFile, "acl-file", "", "File containing JSON-encoded Permissions.")
	cmdRoot.Flags.StringVar(&mountPrefix, "mount-prefix", "vlab", "The mount prefix to use. The published name will be <mount-prefix>/rps/player/<name>.")
	cmdline.HideGlobalFlagsExcept()
	cmdline.Main(cmdRoot)
}

var cmdRoot = &cmdline.Command{
	Runner: v23cmd.RunnerFunc(runPlayer),
	Name:   "rpsplayer",
	Short:  "Implements the Player interface",
	Long: `
Command rpsplayer implements the Player interface, which enables a human to play
the game.
`,
}

func runPlayer(rootctx *context.T, env *cmdline.Env, args []string) error {
	for {
		ctx, _ := vtrace.WithNewTrace(rootctx)
		if selectOne([]string{"Initiate Game", "Wait For Challenge"}) == 0 {
			initiateGame(ctx)
		} else {
			fmt.Println("Waiting to receive a challenge...")
			game := recvChallenge(ctx)
			playGame(ctx, game.address, game.id)
		}
		if selectOne([]string{"Play Again", "Quit"}) == 1 {
			break
		}
	}
	return nil
}

type gameChallenge struct {
	address string
	id      rps.GameId
	opts    rps.GameOptions
}

// impl is a PlayerServerMethods implementation that prompts the user to accept
// or decline challenges. While waiting for a reply from the user, any incoming
// challenges are auto-declined.
type impl struct {
	ch      chan gameChallenge
	decline bool
	lock    sync.Mutex
}

func (i *impl) setDecline(v bool) bool {
	i.lock.Lock()
	defer i.lock.Unlock()
	prev := i.decline
	i.decline = v
	return prev
}

func (i *impl) Challenge(ctx *context.T, call rpc.ServerCall, address string, id rps.GameId, opts rps.GameOptions) error {
	remote, _ := security.RemoteBlessingNames(ctx, call.Security())
	ctx.VI(1).Infof("Challenge (%q, %+v) from %v", address, id, remote)
	// When setDecline(true) returns, future challenges will be declined.
	// Whether the current challenge should be considered depends on the
	// previous state. If 'decline' was already true, we need to decline
	// this challenge. It 'decline' was false, this is the first challenge
	// that we should process.
	if i.setDecline(true) {
		return errors.New("player is busy")
	}
	fmt.Println()
	fmt.Printf("Challenge received from %v for a %d-round ", remote, opts.NumRounds)
	switch opts.GameType {
	case rps.Classic:
		fmt.Print("Classic ")
	case rps.LizardSpock:
		fmt.Print("Lizard-Spock ")
	default:
	}
	fmt.Println("Game.")
	if selectOne([]string{"Accept", "Decline"}) == 0 {
		i.ch <- gameChallenge{address, id, opts}
		return nil
	}
	// Start considering challenges again.
	i.setDecline(false)
	return errors.New("player declined challenge")
}

// recvChallenge runs a server until a game challenge is accepted by the user.
// The server is stopped afterwards.
func recvChallenge(ctx *context.T) gameChallenge {
	ch := make(chan gameChallenge)
	if name == "" {
		name = internal.CreateName(ctx)
	}
	fullname := naming.Join(mountPrefix, "rps", "player", name)
	service := rps.PlayerServer(&impl{ch: ch})
	auth := internal.NewAuthorizer(aclFile)
	ctx, cancel := context.WithCancel(ctx)
	ctx, server, err := v23.WithNewServer(ctx, fullname, service, auth)
	if err != nil {
		ctx.Fatalf("NewServer failed: %v", err)
	}
	ctx.Infof("Listening on endpoint /%s", server.Status().Endpoints[0])
	result := <-ch
	cancel()
	<-server.Closed()
	return result
}

// initiateGame initiates a new game by getting a list of judges and players,
// and asking the user to select one of each, to select the game options, what
// to play, etc.
func initiateGame(ctx *context.T) error {
	jChan := make(chan []string)
	oChan := make(chan []string)
	go findAll(ctx, "judge", jChan)
	go findAll(ctx, "player", oChan)

	fmt.Println("Looking for available participants...")
	judges := <-jChan
	opponents := <-oChan
	fmt.Println()
	if len(judges) == 0 || len(opponents) == 0 {
		return errors.New("no one to play with")
	}

	fmt.Println("Choose a judge:")
	j := selectOne(judges)
	fmt.Println("Choose an opponent:")
	o := selectOne(opponents)
	fmt.Println("Choose the type of rock-paper-scissors game would you like to play:")
	gameType := selectOne([]string{"Classic", "LizardSpock"})
	fmt.Println("Choose the number of rounds required to win:")
	numRounds := selectOne([]string{"1", "2", "3", "4", "5", "6"}) + 1
	gameOpts := rps.GameOptions{NumRounds: int32(numRounds), GameType: rps.GameTypeTag(gameType)}

	gameID, err := createGame(ctx, judges[j], gameOpts)
	if err != nil {
		ctx.Infof("createGame: %v", err)
		return err
	}
	for {
		err := sendChallenge(ctx, opponents[o], judges[j], gameID, gameOpts)
		if err == nil {
			break
		}
		fmt.Printf("Challenge was declined by %s (%v)\n", opponents[o], err)
		fmt.Println("Choose another opponent:")
		o = selectOne(opponents)
	}
	fmt.Println("Joining the game...")

	if _, err = playGame(ctx, judges[j], gameID); err != nil {
		ctx.Infof("playGame: %v", err)
		return err
	}
	return nil
}

func createGame(ctx *context.T, judge string, opts rps.GameOptions) (rps.GameId, error) {
	return rps.JudgeClient(naming.Join(mountPrefix, judge)).CreateGame(ctx, opts)
}

func sendChallenge(ctx *context.T, opponent, judge string, gameID rps.GameId, gameOpts rps.GameOptions) error {
	return rps.PlayerClient(naming.Join(mountPrefix, opponent)).Challenge(ctx, judge, gameID, gameOpts)
}

func playGame(outer *context.T, judge string, gameID rps.GameId) (rps.PlayResult, error) {
	ctx, cancel := context.WithTimeout(outer, 10*time.Minute)
	defer cancel()
	fmt.Println()
	game, err := rps.JudgeClient(naming.Join(mountPrefix, judge)).Play(ctx, gameID)
	if err != nil {
		return rps.PlayResult{}, err
	}
	var playerNum int32
	rStream := game.RecvStream()
	for rStream.Advance() {
		in := rStream.Value()
		switch v := in.(type) {
		case rps.JudgeActionPlayerNum:
			playerNum = v.Value
			fmt.Printf("You are player %d\n", playerNum)
		case rps.JudgeActionOpponentName:
			fmt.Printf("Your opponent is %q\n", v.Value)
		case rps.JudgeActionRoundResult:
			rr := v.Value
			if playerNum != 1 && playerNum != 2 {
				ctx.Fatalf("invalid playerNum: %d", playerNum)
			}
			fmt.Printf("You played %q\n", rr.Moves[playerNum-1])
			fmt.Printf("Your opponent played %q\n", rr.Moves[2-playerNum])
			if len(rr.Comment) > 0 {
				fmt.Printf(">>> %s <<<\n", strings.ToUpper(rr.Comment))
			}
			if rr.Winner == 0 {
				fmt.Println("----- It's a draw -----")
			} else if rps.WinnerTag(playerNum) == rr.Winner {
				fmt.Println("***** You WIN *****")
			} else {
				fmt.Println("##### You LOSE #####")
			}
		case rps.JudgeActionMoveOptions:
			opts := v.Value
			fmt.Println()
			fmt.Println("Choose your weapon:")
			m := selectOne(opts)
			if err := game.SendStream().Send(rps.PlayerActionMove{Value: opts[m]}); err != nil {
				return rps.PlayResult{}, err
			}
		case rps.JudgeActionScore:
			score := v.Value
			fmt.Println()
			fmt.Println("==== GAME SUMMARY ====")
			fmt.Print(internal.FormatScoreCard(score))
			fmt.Println("======================")
			if rps.WinnerTag(playerNum) == score.Winner {
				fmt.Println("You won! :)")
			} else {
				fmt.Println("You lost! :(")
			}
		default:
			outer.Infof("unexpected message type: %T", in)
		}
	}
	if err := rStream.Err(); err == nil {
		fmt.Println("Game Ended")
	} else {
		outer.Infof("stream error: %v", err)
	}

	return game.Finish()
}

func selectOne(choices []string) (choice int) {
	if len(choices) == 0 {
		logger.Global().Fatal("No options to choose from!")
	}
	fmt.Println()
	for i, x := range choices {
		fmt.Printf("  %d. %s\n", i+1, x)
	}
	fmt.Println()
	for {
		if len(choices) == 1 {
			fmt.Print("Select one [1] --> ")
		} else {
			fmt.Printf("Select one [1-%d] --> ", len(choices))
		}
		fmt.Scanf("%d", &choice)
		if choice >= 1 && choice <= len(choices) {
			choice -= 1
			break
		}
	}
	fmt.Println()
	return
}

func findAll(ctx *context.T, t string, out chan []string) {
	ns := v23.GetNamespace(ctx)
	var result []string
	c, err := ns.Glob(ctx, naming.Join(mountPrefix, "rps", t, "*"))
	if err != nil {
		ctx.Infof("ns.Glob failed: %v", err)
		out <- result
		return
	}
	for e := range c {
		switch v := e.(type) {
		case *naming.GlobReplyError:
			fmt.Print("E")
		case *naming.GlobReplyEntry:
			fmt.Print(".")
			result = append(result, strings.TrimPrefix(v.Value.Name, naming.Clean(mountPrefix)+"/"))
		}
	}
	if len(result) == 0 {
		ctx.Infof("found no %ss", t)
		out <- result
		return
	}
	sort.Strings(result)
	out <- result
}
