// 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.

package rpc

import (
	"testing"
	"time"

	"v.io/v23/security"
	"v.io/v23/vdl"
	"v.io/x/ref/test/testutil"
)

func TestDischargeClientCache(t *testing.T) {
	dcc := &dischargeCache{
		cache:    make(map[dischargeCacheKey]security.Discharge),
		idToKeys: make(map[string][]dischargeCacheKey),
	}

	var (
		discharger = testutil.NewPrincipal("discharger")
		expiredCav = mkCaveat(security.NewPublicKeyCaveat(discharger.PublicKey(), "moline", security.ThirdPartyRequirements{}, security.UnconstrainedUse()))
		argsCav    = mkCaveat(security.NewPublicKeyCaveat(discharger.PublicKey(), "moline", security.ThirdPartyRequirements{}, security.UnconstrainedUse()))
		methodCav  = mkCaveat(security.NewPublicKeyCaveat(discharger.PublicKey(), "moline", security.ThirdPartyRequirements{}, security.UnconstrainedUse()))
		serverCav  = mkCaveat(security.NewPublicKeyCaveat(discharger.PublicKey(), "moline", security.ThirdPartyRequirements{}, security.UnconstrainedUse()))

		dExpired = mkDischarge(discharger.MintDischarge(expiredCav, mkCaveat(security.NewExpiryCaveat(time.Now().Add(-1*time.Minute)))))
		dArgs    = mkDischarge(discharger.MintDischarge(argsCav, security.UnconstrainedUse()))
		dMethod  = mkDischarge(discharger.MintDischarge(methodCav, security.UnconstrainedUse()))
		dServer  = mkDischarge(discharger.MintDischarge(serverCav, security.UnconstrainedUse()))

		emptyImp       = security.DischargeImpetus{}
		argsImp        = security.DischargeImpetus{Arguments: []*vdl.Value{&vdl.Value{}}}
		methodImp      = security.DischargeImpetus{Method: "foo"}
		otherMethodImp = security.DischargeImpetus{Method: "bar"}
		serverImp      = security.DischargeImpetus{Server: []security.BlessingPattern{security.BlessingPattern("fooserver")}}
		otherServerImp = security.DischargeImpetus{Server: []security.BlessingPattern{security.BlessingPattern("barserver")}}
	)

	// Discharges for different cavs should not be cached.
	d := mkDischarge(discharger.MintDischarge(argsCav, security.UnconstrainedUse()))
	dcc.Add(d, emptyImp)
	outdis := make([]*security.Discharge, 1)
	if remaining := dcc.Discharges([]security.Caveat{methodCav}, []security.DischargeImpetus{emptyImp}, outdis); remaining == 0 {
		t.Errorf("Discharge for different caveat should not have been in cache")
	}
	dcc.invalidate(d)

	// Add some discharges into the cache.
	dcc.Add(dArgs, argsImp)
	dcc.Add(dMethod, methodImp)
	dcc.Add(dServer, serverImp)
	dcc.Add(dExpired, emptyImp)

	testCases := []struct {
		caveat          security.Caveat           // caveat that we are fetching discharges for.
		queryImpetus    security.DischargeImpetus // Impetus used to  query the cache.
		cachedDischarge *security.Discharge       // Discharge that we expect to be returned from the cache, nil if the discharge should not be cached.
	}{
		// Expired discharges should not be returned by the cache.
		{expiredCav, emptyImp, nil},

		// Discharges with Impetuses that have Arguments should not be cached.
		{argsCav, argsImp, nil},

		{methodCav, methodImp, &dMethod},
		{methodCav, otherMethodImp, nil},
		{methodCav, emptyImp, nil},

		{serverCav, serverImp, &dServer},
		{serverCav, otherServerImp, nil},
		{serverCav, emptyImp, nil},
	}

	for i, test := range testCases {
		out := make([]*security.Discharge, 1)
		remaining := dcc.Discharges([]security.Caveat{test.caveat}, []security.DischargeImpetus{test.queryImpetus}, out)
		if test.cachedDischarge != nil {
			got := "nil"
			if remaining == 0 {
				got = out[0].ID()
			}
			if got != test.cachedDischarge.ID() {
				t.Errorf("#%d: got discharge %v, want %v, queried with %v", i, got, test.cachedDischarge.ID(), test.queryImpetus)
			}
		} else if remaining == 0 {
			t.Errorf("#%d: discharge %v should not have been in cache, queried with %v", i, out[0].ID(), test.queryImpetus)
		}
	}
	if t.Failed() {
		t.Logf("dArgs.ID():    %v", dArgs.ID())
		t.Logf("dMethod.ID():  %v", dMethod.ID())
		t.Logf("dServer.ID():  %v", dServer.ID())
		t.Logf("dExpired.ID(): %v", dExpired.ID())
	}
}

func mkDischarge(d security.Discharge, err error) security.Discharge {
	if err != nil {
		panic(err)
	}
	return d
}
