This commit is contained in:
Florian Dold 2015-12-24 03:20:18 +01:00
parent 4101bc0f53
commit 80f43b85c8
5 changed files with 114 additions and 60 deletions

View File

@ -83,7 +83,8 @@ function getPossibleMintCoins(db, paymentAmount, depositFeeLimit, allowedMints)
req_mints.onsuccess = (e) => { req_mints.onsuccess = (e) => {
let mint = req_mints.result; let mint = req_mints.result;
if (!mint) { if (!mint) {
throw Error("no matching mint in index"); // We don't have that mint ...
return;
} }
let req_coins = tx.objectStore("coins") let req_coins = tx.objectStore("coins")
.index("mintBaseUrl") .index("mintBaseUrl")
@ -99,7 +100,7 @@ function getPossibleMintCoins(db, paymentAmount, depositFeeLimit, allowedMints)
denom: mint.keys.denoms.find((e) => e.denom_pub === value.denomPub) denom: mint.keys.denoms.find((e) => e.denom_pub === value.denomPub)
}; };
if (!cd.denom) { if (!cd.denom) {
throw Error("denom not found"); throw Error("denom not found (database inconsistent)");
} }
let x = m[mint.baseUrl]; let x = m[mint.baseUrl];
if (!x) { if (!x) {
@ -124,18 +125,25 @@ function getPossibleMintCoins(db, paymentAmount, depositFeeLimit, allowedMints)
let maxFee = new Amount(depositFeeLimit); let maxFee = new Amount(depositFeeLimit);
let minAmount = new Amount(paymentAmount); let minAmount = new Amount(paymentAmount);
let accFee = new Amount(coins[0].c.denom.fee_deposit); let accFee = new Amount(coins[0].c.denom.fee_deposit);
let accAmount = new Amount(coins[0].c.coin.currentAmount); let accAmount = Amount.getZero(coins[0].c.coin.currentAmount.currency);
for (let i = 0; i < coins.length; i++) { nextCoin: for (let i = 0; i < coins.length; i++) {
let coinAmount = new Amount(coins[i].c.coin.currentAmount);
let coinFee = coins[i].a;
if (coinAmount.cmp(coinFee) <= 0) {
continue nextCoin;
}
accFee.add(coinFee);
accAmount.add(coinAmount);
if (accFee.cmp(maxFee) >= 0) { if (accFee.cmp(maxFee) >= 0) {
console.log("too much fees");
continue nextMint; continue nextMint;
} }
if (accAmount.cmp(minAmount) >= 0) { if (accAmount.cmp(minAmount) >= 0) {
ret[key] = m[key]; ret[key] = m[key];
continue nextMint; continue nextMint;
} }
accFee.add(coins[i].a);
accFee.add(new Amount(coins[i].c.coin.currentAmount));
} }
console.log(format("mint {0}: acc {1} is not enough for {2}", key, JSON.stringify(accAmount.toJson()), JSON.stringify(minAmount.toJson())));
} }
resolve(ret); resolve(ret);
}; };
@ -161,9 +169,13 @@ function executePay(db, offer, payCoinInfo, merchantBaseUrl, chosenMint) {
payUrl: payUrl.href(), payUrl: payUrl.href(),
payReq: payReq payReq: payReq
}; };
let tx = db.transaction(['transactions'], 'readwrite'); let tx = db.transaction(["transactions", "coins"], "readwrite");
tx.objectStore('transactions').put(t); tx.objectStore('transactions').put(t);
for (let c of payCoinInfo) {
tx.objectStore("coins").put(c.updatedCoin);
}
tx.oncomplete = (e) => { tx.oncomplete = (e) => {
updateBadge(db);
resolve(); resolve();
}; };
}); });
@ -196,7 +208,9 @@ function confirmPay(db, detail, sendResponse) {
} }
function doPayment(db, detail, sendResponse) { function doPayment(db, detail, sendResponse) {
let H_contract = detail.H_contract; let H_contract = detail.H_contract;
let req = db.transaction(['transactions']).objectStore("transactions").get(H_contract); let req = db.transaction(['transactions'])
.objectStore("transactions")
.get(H_contract);
console.log("executing contract", H_contract); console.log("executing contract", H_contract);
req.onsuccess = (e) => { req.onsuccess = (e) => {
console.log("got db response for existing contract"); console.log("got db response for existing contract");
@ -204,7 +218,11 @@ function doPayment(db, detail, sendResponse) {
sendResponse({ success: false, error: "contract not found" }); sendResponse({ success: false, error: "contract not found" });
return; return;
} }
sendResponse({ success: true, payUrl: req.result.payUrl, payReq: req.result.payReq }); sendResponse({
success: true,
payUrl: req.result.payUrl,
payReq: req.result.payReq
});
}; };
return true; return true;
} }
@ -386,11 +404,13 @@ function updateBadge(db) {
req.onsuccess = (e) => { req.onsuccess = (e) => {
let cursor = req.result; let cursor = req.result;
if (cursor) { if (cursor) {
n++; let c = cursor.value;
if (c.currentAmount.fraction != 0 || c.currentAmount.value != 0) {
n++;
}
cursor.continue(); cursor.continue();
} }
else { else {
console.log("badge");
chrome.browserAction.setBadgeText({ text: "" + n }); chrome.browserAction.setBadgeText({ text: "" + n });
chrome.browserAction.setBadgeBackgroundColor({ color: "#0F0" }); chrome.browserAction.setBadgeBackgroundColor({ color: "#0F0" });
} }
@ -576,18 +596,16 @@ function balances(db, detail, sendResponse) {
req.onsuccess = (e) => { req.onsuccess = (e) => {
let cursor = req.result; let cursor = req.result;
if (cursor) { if (cursor) {
tx.objectStore('denoms').get(cursor.value.denomPub).onsuccess = (e2) => { let c = cursor.value;
tx.objectStore('denoms').get(c.denomPub).onsuccess = (e2) => {
let d = e2.target.result; let d = e2.target.result;
let acc = byCurrency[d.value.currency]; let acc = byCurrency[d.value.currency];
if (!acc) { if (!acc) {
acc = new Amount(d.value); acc = Amount.getZero(c.currentAmount.currency);
byCurrency[d.value.currency] = acc.toJson();
}
else {
let am = new Amount(acc);
am.add(new Amount(d.value));
byCurrency[d.value.currency] = am.toJson();
} }
let am = new Amount(c.currentAmount);
am.add(new Amount(acc));
byCurrency[d.value.currency] = am.toJson();
console.log("counting", byCurrency[d.value.currency]); console.log("counting", byCurrency[d.value.currency]);
}; };
cursor.continue(); cursor.continue();

View File

@ -161,7 +161,8 @@ function getPossibleMintCoins(db: IDBDatabase,
req_mints.onsuccess = (e) => { req_mints.onsuccess = (e) => {
let mint: Db.Mint = req_mints.result; let mint: Db.Mint = req_mints.result;
if (!mint) { if (!mint) {
throw Error("no matching mint in index"); // We don't have that mint ...
return;
} }
let req_coins = tx.objectStore("coins") let req_coins = tx.objectStore("coins")
.index("mintBaseUrl") .index("mintBaseUrl")
@ -177,7 +178,7 @@ function getPossibleMintCoins(db: IDBDatabase,
denom: mint.keys.denoms.find((e) => e.denom_pub === value.denomPub) denom: mint.keys.denoms.find((e) => e.denom_pub === value.denomPub)
}; };
if (!cd.denom) { if (!cd.denom) {
throw Error("denom not found"); throw Error("denom not found (database inconsistent)");
} }
let x = m[mint.baseUrl]; let x = m[mint.baseUrl];
if (!x) { if (!x) {
@ -204,18 +205,29 @@ function getPossibleMintCoins(db: IDBDatabase,
let maxFee = new Amount(depositFeeLimit); let maxFee = new Amount(depositFeeLimit);
let minAmount = new Amount(paymentAmount); let minAmount = new Amount(paymentAmount);
let accFee = new Amount(coins[0].c.denom.fee_deposit); let accFee = new Amount(coins[0].c.denom.fee_deposit);
let accAmount = new Amount(coins[0].c.coin.currentAmount); let accAmount = Amount.getZero(coins[0].c.coin.currentAmount.currency);
nextCoin:
for (let i = 0; i < coins.length; i++) { for (let i = 0; i < coins.length; i++) {
let coinAmount = new Amount(coins[i].c.coin.currentAmount);
let coinFee = coins[i].a;
if (coinAmount.cmp(coinFee) <= 0) {
continue nextCoin;
}
accFee.add(coinFee);
accAmount.add(coinAmount);
if (accFee.cmp(maxFee) >= 0) { if (accFee.cmp(maxFee) >= 0) {
console.log("too much fees");
continue nextMint; continue nextMint;
} }
if (accAmount.cmp(minAmount) >= 0) { if (accAmount.cmp(minAmount) >= 0) {
ret[key] = m[key]; ret[key] = m[key];
continue nextMint; continue nextMint;
} }
accFee.add(coins[i].a);
accFee.add(new Amount(coins[i].c.coin.currentAmount));
} }
console.log(format("mint {0}: acc {1} is not enough for {2}",
key,
JSON.stringify(accAmount.toJson()),
JSON.stringify(minAmount.toJson())));
} }
resolve(ret); resolve(ret);
}; };
@ -256,9 +268,13 @@ function executePay(db,
payUrl: payUrl.href(), payUrl: payUrl.href(),
payReq: payReq payReq: payReq
}; };
let tx = db.transaction(['transactions'], 'readwrite'); let tx = db.transaction(["transactions", "coins"], "readwrite");
tx.objectStore('transactions').put(t); tx.objectStore('transactions').put(t);
for (let c of payCoinInfo) {
tx.objectStore("coins").put(c.updatedCoin);
}
tx.oncomplete = (e) => { tx.oncomplete = (e) => {
updateBadge(db);
resolve(); resolve();
}; };
}); });
@ -290,17 +306,18 @@ function confirmPay(db, detail: ConfirmPayRequest, sendResponse) {
}) })
.then(() => { .then(() => {
sendResponse({ sendResponse({
success: true, success: true,
}); });
}); });
return true; return true;
} }
function doPayment(db, detail, sendResponse) { function doPayment(db, detail, sendResponse) {
let H_contract = detail.H_contract; let H_contract = detail.H_contract;
let req = db.transaction(['transactions']).objectStore("transactions").get(H_contract); let req = db.transaction(['transactions'])
.objectStore("transactions")
.get(H_contract);
console.log("executing contract", H_contract); console.log("executing contract", H_contract);
req.onsuccess = (e) => { req.onsuccess = (e) => {
console.log("got db response for existing contract"); console.log("got db response for existing contract");
@ -308,7 +325,11 @@ function doPayment(db, detail, sendResponse) {
sendResponse({success: false, error: "contract not found"}); sendResponse({success: false, error: "contract not found"});
return; return;
} }
sendResponse({success: true, payUrl: req.result.payUrl, payReq: req.result.payReq}); sendResponse({
success: true,
payUrl: req.result.payUrl,
payReq: req.result.payReq
});
}; };
return true; return true;
} }
@ -523,10 +544,12 @@ function updateBadge(db) {
req.onsuccess = (e) => { req.onsuccess = (e) => {
let cursor = req.result; let cursor = req.result;
if (cursor) { if (cursor) {
n++; let c: Db.Coin = cursor.value;
if (c.currentAmount.fraction != 0 || c.currentAmount.value != 0) {
n++;
}
cursor.continue(); cursor.continue();
} else { } else {
console.log("badge");
chrome.browserAction.setBadgeText({text: "" + n}); chrome.browserAction.setBadgeText({text: "" + n});
chrome.browserAction.setBadgeBackgroundColor({color: "#0F0"}); chrome.browserAction.setBadgeBackgroundColor({color: "#0F0"});
} }
@ -729,17 +752,16 @@ function balances(db, detail, sendResponse) {
req.onsuccess = (e) => { req.onsuccess = (e) => {
let cursor = req.result; let cursor = req.result;
if (cursor) { if (cursor) {
tx.objectStore('denoms').get(cursor.value.denomPub).onsuccess = (e2) => { let c: Db.Coin = cursor.value;
tx.objectStore('denoms').get(c.denomPub).onsuccess = (e2) => {
let d = e2.target.result; let d = e2.target.result;
let acc = byCurrency[d.value.currency]; let acc = byCurrency[d.value.currency];
if (!acc) { if (!acc) {
acc = new Amount(d.value); acc = Amount.getZero(c.currentAmount.currency);
byCurrency[d.value.currency] = acc.toJson();
} else {
let am = new Amount(acc);
am.add(new Amount(d.value));
byCurrency[d.value.currency] = am.toJson();
} }
let am = new Amount(c.currentAmount);
am.add(new Amount(acc));
byCurrency[d.value.currency] = am.toJson();
console.log("counting", byCurrency[d.value.currency]); console.log("counting", byCurrency[d.value.currency]);
}; };
cursor.continue(); cursor.continue();

View File

@ -55,25 +55,32 @@ document.addEventListener('taler-execute-payment', function (e) {
}, },
}; };
chrome.runtime.sendMessage(msg, (resp) => { chrome.runtime.sendMessage(msg, (resp) => {
console.log("got backend response to execute-payment:", JSON.stringify(resp));
if (!resp.success) { if (!resp.success) {
console.log("failure!"); console.log("failure!");
return; return;
} }
console.log("Making request to ", resp.payUrl);
let r = new XMLHttpRequest(); let r = new XMLHttpRequest();
r.open('post', resp.payUrl); r.open('post', resp.payUrl);
r.send(JSON.stringify(resp.payReq)); r.send(JSON.stringify(resp.payReq));
let evt; let detail = {};
r.onload = (e) => { r.onload = (e) => {
if (r.status != 200) { switch (r.status) {
console.log("non-200 error"); case 200:
console.log(r.responseText); detail.success = true;
alert("merchant returned HTTP status " + r.status); break;
case 301:
detail.success = true;
console.log("Headers:", r.getAllResponseHeaders());
detail.fulfillmentUrl = r.getResponseHeader('Location');
break;
default:
detail.success = false;
break;
} }
else { console.log("status was:", r.status);
evt = new CustomEvent("taler-payment-result", { detail: resp }); console.log("detail:", JSON.stringify(detail));
} document.dispatchEvent(new CustomEvent("taler-payment-result", { detail: detail }));
document.dispatchEvent(evt);
}; };
}); });
}); });

View File

@ -63,24 +63,32 @@ document.addEventListener('taler-execute-payment', function(e: CustomEvent) {
}, },
}; };
chrome.runtime.sendMessage(msg, (resp) => { chrome.runtime.sendMessage(msg, (resp) => {
console.log("got backend response to execute-payment:", JSON.stringify(resp));
if (!resp.success) { if (!resp.success) {
console.log("failure!"); console.log("failure!");
return; return;
} }
console.log("Making request to ", resp.payUrl);
let r = new XMLHttpRequest(); let r = new XMLHttpRequest();
r.open('post', resp.payUrl); r.open('post', resp.payUrl);
r.send(JSON.stringify(resp.payReq)); r.send(JSON.stringify(resp.payReq));
let evt; let detail: any = {};
r.onload = (e) => { r.onload = (e) => {
if (r.status != 200) { switch (r.status) {
console.log("non-200 error"); case 200:
console.log(r.responseText); detail.success = true;
alert("merchant returned HTTP status " + r.status); break;
} else { case 301:
evt = new CustomEvent("taler-payment-result", {detail: resp}); detail.success = true;
console.log("Headers:", r.getAllResponseHeaders());
detail.fulfillmentUrl = r.getResponseHeader('Location');
break;
default:
detail.success = false;
break;
} }
document.dispatchEvent(evt); console.log("status was:", r.status);
console.log("detail:", JSON.stringify(detail));
document.dispatchEvent(new CustomEvent("taler-payment-result", {detail: detail}));
}; };
}); });
}); });

View File

@ -7,7 +7,6 @@
<script src="../lib/handlebars-v4.0.5.js"></script> <script src="../lib/handlebars-v4.0.5.js"></script>
<script src="../lib/commonHelpers.js"></script> <script src="../lib/commonHelpers.js"></script>
<script src="confirm-contract.js"></script> <script src="confirm-contract.js"></script>
<link rel="stylesheet" type="text/css" href="../style/page.css">
<link rel="stylesheet" type="text/css" href="../style/wallet.css"> <link rel="stylesheet" type="text/css" href="../style/wallet.css">
<script id="contract-template" type="text/x-handlebars-template"> <script id="contract-template" type="text/x-handlebars-template">
@ -45,8 +44,8 @@
<article id="contract"> <article id="contract">
<div id="render-contract"></div> <div id="render-contract"></div>
<button id="confirm-pay">Confirm Payment</button> <button id="confirm-pay">Confirm Payment</button>
<div id="confirm-warning"></div>
</article> </article>
<article id="status"></article> <article id="status"></article>