Skip to content

Commit

Permalink
Merge pull request #53 from JSKitty/fix-rounding-and-lint-error
Browse files Browse the repository at this point in the history
[Fix] TX precision loss and Linting errors
  • Loading branch information
scrnetto committed Aug 13, 2023
2 parents 450a52b + 5581ea5 commit 3b1591b
Show file tree
Hide file tree
Showing 4 changed files with 32 additions and 28 deletions.
20 changes: 10 additions & 10 deletions public/index.html
Expand Up @@ -1151,7 +1151,7 @@ <h4>This collection is empty!</h4>

function sendTransactionGUI() {
const coinSelection = document.getElementById("sendingCoinVal").value;
let nAmountSats = Number(document.getElementById("sendAmount").value.trim()) * COIN;
let nAmountSats = Math.round(Number(document.getElementById("sendAmount").value.trim()) * COIN);
const sendAddress = document.getElementById("sendAddress").value.trim();
if (!nAmountSats || !Number.isInteger(nAmountSats)) {
return M.toast({html: 'Please enter a valid amount!', displayLength: 2000});
Expand Down Expand Up @@ -1364,7 +1364,7 @@ <h4>This collection is empty!</h4>
const cTx = WALLET.sccjs.wallet.tx.transaction();
// Inputs
const strAddr = WALLET.getActiveWallet().getPubkey();
const nDeployCost = (nDeployFee * COIN) + 1000;
const nDeployCost = Math.round((nDeployFee * COIN) + 1000);
const usedUTXOs = WALLET.getCoinsToSpend(nDeployCost, false, strAddr);
const nUTXOs = usedUTXOs.reduce((a, b) => a + b.sats, 0);
for (const cUTXO of usedUTXOs)
Expand All @@ -1376,7 +1376,7 @@ <h4>This collection is empty!</h4>
cTx.addoutput(strDeployFeeDest, nDeployFee);
// Fee & Change output
const nFee = WALLET.getFee(cTx.serialize().length);
const nSpent = nFee + (nDeployFee * COIN);
const nSpent = Math.round(nFee + (nDeployFee * COIN));
const nChange = nUTXOs - nSpent;
cTx.addoutput(strAddr, nChange / COIN);
// Broadcast
Expand Down Expand Up @@ -2630,7 +2630,7 @@ <h4 class="mb-5 theme-color-secondary font-weight-bold">Create Token</h4>
if (domScpTokenSupply.value.length) {
// Remove all whitespace
domScpTokenSupply.value = domScpTokenSupply.value.replace(/ /g, '').trim();
const nSupply = Number(domScpTokenSupply.value * COIN);
const nSupply = Math.round(Number(domScpTokenSupply.value.trim()) * COIN);
// Supply must be 1 coin minimum
if (nSupply < COIN) {
domScpTokenErrors.innerHTML += 'Supply: Minimum is 1!<br>';
Expand All @@ -2652,18 +2652,18 @@ <h4 class="mb-5 theme-color-secondary font-weight-bold">Create Token</h4>
if (domScpTokenPoSReward.value.length) {
// Remove all whitespace
domScpTokenPoSReward.value = domScpTokenPoSReward.value.replace(/ /g, '').trim();
const nReward = Number(domScpTokenPoSReward.value * COIN);
const nReward = Math.round(Number(domScpTokenPoSReward.value.trim()) * COIN);
// Reward must be a number
if (!Number.isFinite(nReward)) {
domScpTokenErrors.innerHTML += 'Rewards: Must be a number!<br>';
isComplete = false;
}
// Reward cannot be smaller than 0.0001 coins
if (nReward < (0.001 * COIN)) {
if (nReward < Math.round(0.001 * COIN)) {
domScpTokenErrors.innerHTML += 'Rewards: Cannot be smaller than 0.0001!<br>';
isComplete = false;
}
const nSupply = Number(domScpTokenSupply.value * COIN);
const nSupply = Math.round(Number(domScpTokenSupply.value.trim()) * COIN);
// Reward cannot be equal to the max supply
if (nReward === nSupply) {
domScpTokenErrors.innerHTML += 'Rewards: Cannot be equal to the max supply!<br>';
Expand Down Expand Up @@ -2769,7 +2769,7 @@ <h4 class="mb-5 theme-color-secondary font-weight-bold">Create Token</h4>
// Ticker
arrParams.push(domScpTokenTicker.value);
// Supply
arrParams.push((Number(domScpTokenSupply.value) * COIN).toString());
arrParams.push((Number(domScpTokenSupply.value.trim()) * COIN).toString());
}

// SCP-2 Spec
Expand All @@ -2779,9 +2779,9 @@ <h4 class="mb-5 theme-color-secondary font-weight-bold">Create Token</h4>
// Ticker
arrParams.push(domScpTokenTicker.value);
// Supply
arrParams.push((Number(domScpTokenSupply.value) * COIN).toString());
arrParams.push(Math.round(Number(domScpTokenSupply.value.trim()) * COIN).toString());
// PoS Reward
arrParams.push((Number(domScpTokenPoSReward.value) * COIN).toString());
arrParams.push(Math.round(Number(domScpTokenPoSReward.value.trim()) * COIN).toString());
// Min Stake Age
arrParams.push(domScpTokenMinAge.value);
}
Expand Down
14 changes: 9 additions & 5 deletions src/api/wallet.controller.js
Expand Up @@ -138,7 +138,7 @@ async function send(req, res) {
const strAddr = req.params.address;
const strCurrency = req.params.currency;
const strTo = req.params.to;
const nSentSats = Number(req.params.amount) * COIN;
const nSentSats = Math.round(Number(req.params.amount) * COIN);
try {
// Cache our tokens list, for if needed
let cTokens = false;
Expand All @@ -154,7 +154,7 @@ async function send(req, res) {
// Ensure the 'amount' is a valid number
if (Number.isNaN(nSentSats) || !Number.isInteger(nSentSats)) {
return res.status(400)
.send('Sending amount "' + (nSentSats / COIN) +
.send('Sending amount (in satoshis) "' + nSentSats +
'" is an invalid amount!');
}

Expand Down Expand Up @@ -224,7 +224,9 @@ async function send(req, res) {
const strSignedTx = await cTx.sign(cWallet.getPrivkey(), 1);
const strTXID = await ptrWALLET.broadcastTx(strSignedTx);
// Mark UTXOs as spent
usedUTXOs.forEach(cUTXO => cUTXO.spent = true);
usedUTXOs.forEach(cUTXO => {
cUTXO.spent = true;
});
return res.json({
'txid': strTXID,
'rawTx': strSignedTx
Expand Down Expand Up @@ -431,7 +433,9 @@ async function createCollection(req, res) {
const strSignedTx = await cTx.sign(cWallet.getPrivkey(), 1);
const strTXID = await ptrWALLET.broadcastTx(strSignedTx);
// Mark UTXOs as spent
usedUTXOs.forEach(cUTXO => cUTXO.spent = true);
usedUTXOs.forEach(cUTXO => {
cUTXO.spent = true;
});
// Return API data
return res.json({
'txid': strTXID,
Expand Down Expand Up @@ -600,7 +604,7 @@ async function burnNFT(req, res) {
strContract + ' destroy ' + strID);
// Fee & Change output
const nFee = ptrWALLET.getFee(cTx.serialize().length);
const nChange = cUTXO.sats - nFee
const nChange = cUTXO.sats - nFee;
cTx.addoutput(strPubkey, nChange / COIN);
// Broadcast
const strSignedTx = await cTx.sign(cWallet.getPrivkey(), 1);
Expand Down
6 changes: 3 additions & 3 deletions src/index.js
Expand Up @@ -32,9 +32,9 @@ let isOutdated = false;

// Main Modules
let npmPackage;
let DB, NET,
RPC = require("@jskitty/bitcoin-rpc"),
TOKENS, NFT, WALLET, UPGRADES, VM;
let DB; let NET;
const RPC = require('@jskitty/bitcoin-rpc');
let TOKENS; let NFT; let WALLET; let UPGRADES; let VM;

// API Modules
let apiACTIVITY, apiBLOCKCHAIN, apiTOKENS, apiWALLET, apiIO;
Expand Down
20 changes: 10 additions & 10 deletions src/token.js
Expand Up @@ -112,7 +112,7 @@ class SCP1Token {
debitAccount(address, amount, tx) {
// Ensure expended debit does not bring the supply into the negative
if ((this.supply - amount) < 0) {
console.error("SCP-" + this.version + ": Attempted burn of '" +
console.error('SCP-' + this.version + ": Attempted burn of '" +
amount + "' for token '" + this.name +
"' brings the supply into the negative!");
return false;
Expand All @@ -129,12 +129,12 @@ class SCP1Token {
'amount': amount
});
this.supply -= amount;
console.log("SCP-" + this.version + ": User for token '" +
console.log('SCP-' + this.version + ": User for token '" +
this.name + "' burned '" + amount + ' ' + this.ticker +
"', new balance is '" + cAcc.balance +
"', new supply is '" + this.supply + "'!");
} else {
console.log("SCP-" + this.version + ": Attempted burn of token '" +
console.log('SCP-' + this.version + ": Attempted burn of token '" +
this.name + "' of amount '" + amount +
' ' + this.ticker +
"' failed due to insufficient funds!");
Expand All @@ -151,7 +151,7 @@ class SCP1Token {

// Ensure the lock cannot be 'reversed' via negative locks
if (amount <= 0) {
console.error("SCP-" + this.version + ": Attempted reverse lock " +
console.error('SCP-' + this.version + ': Attempted reverse lock ' +
"of '" + amount + "' for token '" +
this.name + "' was rejected");
return false;
Expand All @@ -160,7 +160,7 @@ class SCP1Token {
// Ensure locked tokens do not exceed the account spendable balance
const nSpendable = cAcc.balance - cAcc.lockedBalance;
if (amount > nSpendable) {
console.error("SCP-" + this.version + ": Attempted lock of '" +
console.error('SCP-' + this.version + ": Attempted lock of '" +
amount + "' for token '" +
this.name + "' exceeds spendable balance of '" +
nSpendable + "'!");
Expand All @@ -176,7 +176,7 @@ class SCP1Token {
'amount': amount
});

console.log("SCP-" + this.version + ": User for token '" +
console.log('SCP-' + this.version + ": User for token '" +
this.name + "' locked '" + amount + ' ' + this.ticker +
"', new spendable balance is '" +
(cAcc.balance - cAcc.lockedBalance) + ' ' + this.ticker +
Expand All @@ -192,15 +192,15 @@ class SCP1Token {

// Ensure the unlock cannot be 'reversed' via negative unlocks
if (amount <= 0) {
console.error("SCP-" + this.version + ": Attempted reverse unlock " +
console.error('SCP-' + this.version + ': Attempted reverse unlock ' +
"of '" + amount + "' for token '" +
this.name + "' was rejected");
return false;
}

// Ensure we have enough locked coins to unlock
if (amount > cAcc.lockedBalance) {
console.error("SCP-" + this.version + ": Attempted lock of '" +
console.error('SCP-' + this.version + ": Attempted lock of '" +
amount + "' for token '" +
this.name + "' exceeds locked balance of '" +
cAcc.lockedBalance + "'!");
Expand All @@ -216,7 +216,7 @@ class SCP1Token {
'amount': amount
});

console.log("SCP-" + this.version + ": User for token '" +
console.log('SCP-' + this.version + ": User for token '" +
this.name + "' unlocked '" + amount + ' ' + this.ticker +
"', new spendable balance is '" +
(cAcc.balance - cAcc.lockedBalance) + ' ' + this.ticker +
Expand All @@ -230,7 +230,7 @@ class SCP1Token {
if (!this.debitAccount(acc1, amount, tx)) return;
// Credit the tokens to the second account
this.creditAccount(acc2, amount, tx);
console.log("SCP-" + this.version + ": User for token '" + this.name +
console.log('SCP-' + this.version + ": User for token '" + this.name +
"' transferred '" + amount + ' ' + this.ticker +
"' to another account!\nFrom: (" + acc1 + '), To: (' +
acc2 + ')');
Expand Down

0 comments on commit 3b1591b

Please sign in to comment.