Exemple #1
0
// Computes the total balance for a cipher.Address's coin.UxOuts
func (self *Visor) balance(uxs coin.UxArray) wallet.Balance {
	prevTime := self.blockchain.Time()
	b := wallet.NewBalance(0, 0)
	for _, ux := range uxs {
		b = b.Add(wallet.NewBalance(ux.Body.Coins, ux.CoinHours(prevTime)))
	}
	return b
}
Exemple #2
0
// Computes the total balance for cipher.Addresses and their coin.UxOuts
func (self *Visor) totalBalance(auxs coin.AddressUxOuts) wallet.Balance {
	prevTime := self.blockchain.Time()
	b := wallet.NewBalance(0, 0)
	for _, uxs := range auxs {
		for _, ux := range uxs {
			b = b.Add(wallet.NewBalance(ux.Body.Coins, ux.CoinHours(prevTime)))
		}
	}
	return b
}
Exemple #3
0
// Creates and broadcasts a transaction sending money from one of our wallets
// to destination address.
func walletSpendHandler(gateway *daemon.Gateway) http.HandlerFunc {
	return func(w http.ResponseWriter, r *http.Request) {

		//log.Printf("Spend1")

		if r.FormValue("id") == "" {
			Error400(w, "Missing wallet_id")
			return
		}

		walletId := wallet.WalletID(r.FormValue("id"))
		if walletId == "" {
			Error400(w, "Invalid Wallet Id")
			return
		}
		sdst := r.FormValue("dst")
		if sdst == "" {
			Error400(w, "Missing destination address \"dst\"")
			return
		}
		dst, err := cipher.DecodeBase58Address(sdst)
		if err != nil {
			//Error400(w, "Invalid destination address: %v", err)
			Error400(w, "Invalid destination address: %v", err.Error())
			return
		}

		//set fee automatically for now
		/*
			sfee := r.FormValue("fee")
			fee, err := strconv.ParseUint(sfee, 10, 64)
			if err != nil {
				Error400(w, "Invalid \"fee\" value")
				return
			}
		*/
		//var fee uint64 = 0

		scoins := r.FormValue("coins")
		//shours := r.FormValue("hours")
		coins, err := strconv.ParseUint(scoins, 10, 64)
		if err != nil {
			Error400(w, "Invalid \"coins\" value")
			return
		}

		var hours uint64 = 0
		var fee uint64 = 0 //doesnt work/do anything right now

		//MOVE THIS INTO HERE
		ret := Spend(gateway.D, gateway.D.Visor, Wg, walletId, wallet.NewBalance(coins, hours), fee, dst)

		if ret.Error != "" {
			Error400(w, "Spend Failed: %s", ret.Error)
		}
		SendOr404(w, ret)
	}
}
Exemple #4
0
// Creates a Transaction spending coins and hours from our coins
func CreateSpendingTransaction(wlt wallet.Wallet,
	unconfirmed *UnconfirmedTxnPool, unspent *coin.UnspentPool,
	headTime uint64, amt wallet.Balance, fee, burnFactor uint64,
	dest cipher.Address) (coin.Transaction, error) {
	txn := coin.Transaction{}
	auxs := unspent.AllForAddresses(wlt.GetAddresses())
	// Subtract pending spends from available
	puxs := unconfirmed.SpendsForAddresses(unspent, wlt.GetAddressSet())
	auxs = auxs.Sub(puxs)

	// Determine which unspents to spend
	spends, err := createSpends(headTime, auxs.Flatten(), amt, fee, burnFactor)
	if err != nil {
		return txn, err
	}

	// Add these unspents as tx inputs
	toSign := make([]cipher.SecKey, len(spends))
	spending := wallet.Balance{0, 0}
	for i, au := range spends {
		entry, exists := wlt.GetEntry(au.Body.Address)
		if !exists {
			log.Panic("On second thought, the wallet entry does not exist")
		}
		txn.PushInput(au.Hash())
		toSign[i] = entry.Secret
		spending.Coins += au.Body.Coins
		spending.Hours += au.CoinHours(headTime)
	}

	// Determine how much change we get back, if any
	_, changeHours, err := calculateBurnAndChange(spending.Hours,
		amt.Hours, fee, burnFactor)
	if err != nil {
		// This should not occur, else createSpends is broken
		return txn, err
	}
	change := wallet.NewBalance(spending.Coins-amt.Coins, changeHours)
	// TODO -- send change to a new address
	changeAddr := spends[0].Body.Address
	if change.Coins == 0 {
		if change.Hours > 0 {
			msg := ("Have enough coins, but not enough to send coin hours " +
				"change back. Would spend %d more hours than requested.")
			return txn, fmt.Errorf(msg, change.Hours)
		}
	} else {
		txn.PushOutput(changeAddr, change.Coins, change.Hours)
	}

	// Finalize the the transaction
	txn.PushOutput(dest, amt.Coins, amt.Hours)
	txn.SignInputs(toSign)
	txn.UpdateHeader()
	return txn, nil
}
Exemple #5
0
//DEPRECATE
//deprecate dependency on wallet
// Creates a Transaction spending coins and hours from our coins
//MOVE SOMEWHERE ELSE
//Move to wallet or move to ???
func CreateSpendingTransaction(wlt wallet.Wallet,
	unconfirmed *UnconfirmedTxnPool, unspent *coin.UnspentPool,
	headTime uint64, amt wallet.Balance,
	dest cipher.Address) (coin.Transaction, error) {
	txn := coin.Transaction{}
	auxs := unspent.AllForAddresses(wlt.GetAddresses())
	// Subtract pending spends from available
	puxs := unconfirmed.SpendsForAddresses(unspent, wlt.GetAddressSet())
	auxs = auxs.Sub(puxs)

	// Determine which unspents to spend
	spends, err := createSpends(headTime, auxs.Flatten(), amt)
	if err != nil {
		return txn, err
	}

	// Add these unspents as tx inputs
	toSign := make([]cipher.SecKey, len(spends))
	spending := wallet.Balance{0, 0}
	for i, au := range spends {
		entry, exists := wlt.GetEntry(au.Body.Address)
		if !exists {
			log.Panic("On second thought, the wallet entry does not exist")
		}
		txn.PushInput(au.Hash())
		toSign[i] = entry.Secret
		spending.Coins += au.Body.Coins
		spending.Hours += au.CoinHours(headTime)
	}

	//keep 1/4th of hours as change
	//send half to each address
	var changeHours uint64 = spending.Hours / 4

	if amt.Coins == spending.Coins {
		txn.PushOutput(dest, amt.Coins, changeHours/2)
		txn.SignInputs(toSign)
		txn.UpdateHeader()
		return txn, nil
	}

	change := wallet.NewBalance(spending.Coins-amt.Coins, changeHours/2)
	// TODO -- send change to a new address
	changeAddr := spends[0].Body.Address

	//create transaction
	txn.PushOutput(changeAddr, change.Coins, change.Hours)
	txn.PushOutput(dest, amt.Coins, changeHours/2)
	txn.SignInputs(toSign)
	txn.UpdateHeader()
	return txn, nil
}
Exemple #6
0
// Creates and broadcasts a transaction sending money from one of our wallets
// to destination address.
func walletSpendHandler(gateway *daemon.Gateway) http.HandlerFunc {
	return func(w http.ResponseWriter, r *http.Request) {
		walletId := wallet.WalletID(r.FormValue("id"))
		if walletId == "" {
			Error400(w, "Missing wallet_id")
			return
		}
		sdst := r.FormValue("dst")
		if sdst == "" {
			Error400(w, "Missing destination address \"dst\"")
			return
		}
		dst, err := cipher.DecodeBase58Address(sdst)
		if err != nil {
			Error400(w, "Invalid destination address")
			return
		}
		sfee := r.FormValue("fee")
		fee, err := strconv.ParseUint(sfee, 10, 64)
		if err != nil {
			Error400(w, "Invalid \"fee\" value")
			return
		}
		scoins := r.FormValue("coins")
		shours := r.FormValue("hours")
		coins, err := strconv.ParseUint(scoins, 10, 64)
		if err != nil {
			Error400(w, "Invalid \"coins\" value")
			return
		}
		hours, err := strconv.ParseUint(shours, 10, 64)
		if err != nil {
			Error400(w, "Invalid \"hours\" value")
			return
		}
		SendOr404(w, gateway.Spend(walletId, wallet.NewBalance(coins, hours),
			fee, dst))
	}
}