package notary

import (
	"slices"

	"git.marketally.com/tutus-one/tutus-chain/pkg/crypto/keys"
	"git.marketally.com/tutus-one/tutus-chain/pkg/encoding/address"
	"git.marketally.com/tutus-one/tutus-chain/pkg/util"
	"git.marketally.com/tutus-one/tutus-chain/pkg/wallet"
	"go.uber.org/zap"
)

// UpdateNotaryNodes implements Notary interface and updates current notary account.
func (n *Notary) UpdateNotaryNodes(notaryNodes keys.PublicKeys) {
	n.accMtx.Lock()
	defer n.accMtx.Unlock()

	if n.currAccount != nil && slices.ContainsFunc(notaryNodes, n.currAccount.PublicKey().Equal) {
		return
	}

	var acc *wallet.Account
	for _, node := range notaryNodes {
		acc = n.wallet.GetAccount(node.GetScriptHash())
		if acc != nil {
			if acc.CanSign() {
				break
			}
			err := acc.Decrypt(n.Config.MainCfg.UnlockWallet.Password, n.wallet.Scrypt)
			if err != nil {
				n.Config.Log.Warn("can't unlock notary node account",
					zap.String("address", address.Uint160ToString(acc.Contract.ScriptHash())),
					zap.Error(err))
				acc = nil
			}
			break
		}
	}

	n.currAccount = acc
	if acc == nil {
		n.reqMtx.Lock()
		n.requests = make(map[util.Uint256]*request)
		n.reqMtx.Unlock()
	}
}

func (n *Notary) getAccount() *wallet.Account {
	n.accMtx.RLock()
	defer n.accMtx.RUnlock()
	return n.currAccount
}
