Logic for Wallet notifications; some bugfixes

This commit is contained in:
Zach Fox 2018-09-18 12:28:03 -07:00
parent c453594eb7
commit a97f9eb79a
4 changed files with 131 additions and 19 deletions

View file

@ -155,8 +155,8 @@ function AppUi(properties) {
return;
}
// User is "appearing offline"
if (GlobalServices.findableBy === "none") {
// User is "appearing offline", or is offline, or the app is open
if (GlobalServices.findableBy === "none" || Account.username === "" || that.isOpen) {
that.notificationPollTimeout = Script.setTimeout(that.notificationPoll, that.notificationPollTimeoutMs);
return;
}
@ -164,7 +164,10 @@ function AppUi(properties) {
var url = METAVERSE_BASE + that.notificationPollEndpoint;
if (that.notificationPollCaresAboutSince) {
url = url + "&since=" + (new Date().getTime());
var settingsKey = "notifications/" + that.buttonName + "/lastSince";
var timestamp = Settings.getValue(settingsKey, new Date().getTime());
url = url + "&since=" + timestamp;
Settings.setValue(settingsKey, timestamp);
}
console.debug(that.buttonName, 'polling for notifications at endpoint', url);
@ -203,7 +206,8 @@ function AppUi(properties) {
// This won't do anything if there isn't a notification endpoint set
that.notificationPoll();
function availabilityChanged() {
function restartNotificationPoll() {
that.notificationInitialCallbackMade = false;
if (that.notificationPollTimeout) {
Script.clearTimeout(that.notificationPollTimeout);
that.notificationPollTimeout = false;
@ -303,7 +307,8 @@ function AppUi(properties) {
} : that.ignore;
that.onScriptEnding = function onScriptEnding() {
// Close if necessary, clean up any remaining handlers, and remove the button.
GlobalServices.findableByChanged.disconnect(availabilityChanged);
GlobalServices.myUsernameChanged.disconnect(restartNotificationPoll);
GlobalServices.findableByChanged.disconnect(restartNotificationPoll);
if (that.isOpen) {
that.close();
}
@ -323,6 +328,7 @@ function AppUi(properties) {
that.tablet.screenChanged.connect(that.onScreenChanged);
that.button.clicked.connect(that.onClicked);
Script.scriptEnding.connect(that.onScriptEnding);
GlobalServices.findableByChanged.connect(availabilityChanged);
GlobalServices.findableByChanged.connect(restartNotificationPoll);
GlobalServices.myUsernameChanged.connect(restartNotificationPoll);
}
module.exports = AppUi;

View file

@ -19,7 +19,7 @@ module.exports = {
// ------------------------------------------------------------------
request: function (options, callback) { // cb(error, responseOfCorrectContentType) of url. A subset of npm request.
var httpRequest = new XMLHttpRequest(), key;
var httpRequest = new XMLHttpRequest(), key;
// QT bug: apparently doesn't handle onload. Workaround using readyState.
httpRequest.onreadystatechange = function () {
var READY_STATE_DONE = 4;
@ -72,7 +72,7 @@ module.exports = {
}
httpRequest.open(options.method, options.uri, true);
httpRequest.send(options.body || null);
}
}
};
// ===========================================================================================

View file

@ -491,12 +491,110 @@ function walletOpened() {
Controller.mouseMoveEvent.connect(handleMouseMoveEvent);
triggerMapping.enable();
triggerPressMapping.enable();
ui.messagesWaiting(false);
}
function walletClosed() {
off();
}
function notificationDataProcessPage(data) {
return data.data.history;
}
var shouldShowDot = false;
function notificationPollCallback(historyArray) {
var i;
var someoneElsePurchasedArray = [];
var proofIssuedArray = [];
var moneyReceivedArray = [];
var giftReceivedArray = [];
for (i = 0; i < historyArray.length; i++) {
var currentHistoryTxn = historyArray[i];
if (currentHistoryTxn.sent_certs <= 0 &&
currentHistoryTxn.received_certs <= 0) {
// This is an HFC transfer.
if (currentHistoryTxn.received_money > 0) {
if (currentHistoryTxn.sender_name === "marketplace") {
someoneElsePurchasedArray.push(currentHistoryTxn);
} else {
moneyReceivedArray.push(currentHistoryTxn);
}
}
} else if (currentHistoryTxn.sent_money <= 0 &&
currentHistoryTxn.received_money <= 0 &&
currentHistoryTxn.received_certs > 0) {
// This is a non-HFC asset transfer.
if (currentHistoryTxn.sender_name === "marketplace") {
proofIssuedArray.push(currentHistoryTxn);
} else {
giftReceivedArray.push(currentHistoryTxn);
}
}
}
if (!ui.isOpen) {
shouldShowDot = shouldShowDot ||
(someoneElsePurchasedArray.length > 0) ||
(proofIssuedArray.length > 0) ||
(moneyReceivedArray.length > 0) ||
(giftReceivedArray.length > 0);
ui.messagesWaiting(shouldShowDot);
var notificationCount = someoneElsePurchasedArray.length +
proofIssuedArray.length +
moneyReceivedArray.length +
giftReceivedArray.length;
if (notificationCount > 0) {
var message;
if (!ui.notificationInitialCallbackMade) {
message = "You have " + notificationCount + " unread wallet " +
"notification" + (notificationCount === 1 ? "" : "s") + "! Open WALLET to see all activity.";
ui.notificationDisplayBanner(message);
} else {
var currentItemName, senderName;
for (i = 0; i < someoneElsePurchasedArray.length; i++) {
currentItemName = (someoneElsePurchasedArray[i].message).match('<a href=".*">(.*)</a>')[1];
message = "Someone purchased your item \"" + currentItemName + "\" from the Marketplace! " +
"Open WALLET to see all activity.";
ui.notificationDisplayBanner(message);
}
for (i = 0; i < proofIssuedArray.length; i++) {
currentItemName = (proofIssuedArray[i].message).match('<a href=".*">(.*)</a>')[1];
message = "You have been issued a proof for your Marketplace item \"" + currentItemName + "\"! " +
"Open WALLET to see all activity.";
ui.notificationDisplayBanner(message);
}
for (i = 0; i < moneyReceivedArray.length; i++) {
senderName = moneyReceivedArray[i].sender_name;
if (senderName === "") {
senderName = "Someone";
}
message = senderName + " sent you " + moneyReceivedArray[i].received_money + " HFC! " +
"Open WALLET to see all activity.";
ui.notificationDisplayBanner(message);
}
for (i = 0; i < giftReceivedArray.length; i++) {
senderName = giftReceivedArray[i].sender_name;
if (senderName === "") {
senderName = "Someone";
}
message = senderName + " sent you a gift! " +
"Open WALLET to see all activity.";
ui.notificationDisplayBanner(message);
}
}
}
}
}
function isReturnedDataEmpty(data) {
var historyArray = data.data.history;
return historyArray.length === 0;
}
//
// Manage the connection between the button and the window.
//
@ -510,7 +608,13 @@ function startup() {
home: WALLET_QML_SOURCE,
onOpened: walletOpened,
onClosed: walletClosed,
onMessage: fromQml
onMessage: fromQml,
notificationPollEndpoint: "/api/v1/notifications?source=commerce-history&per_page=10",
notificationPollTimeoutMs: 60000,
notificationDataProcessPage: notificationDataProcessPage,
notificationPollCallback: notificationPollCallback,
notificationPollStopPaginatingConditionMet: isReturnedDataEmpty,
notificationPollCaresAboutSince: true
});
GlobalServices.myUsernameChanged.connect(onUsernameChanged);
}

View file

@ -874,16 +874,18 @@ function notificationPollCallback(connectionsArray) {
shouldShowDot: shouldShowDot
});
var message;
if (!ui.notificationInitialCallbackMade) {
message = newlyOnlineConnectionsArray.length + " of your connections " +
(newlyOnlineConnectionsArray.length === 1 ? "is" : "are") + " online. Open PEOPLE to join them!";
ui.notificationDisplayBanner(message);
} else {
for (i = 0; i < newlyOnlineConnectionsArray.length; i++) {
message = newlyOnlineConnectionsArray[i].username + " is available in " +
newlyOnlineConnectionsArray[i].location.root.name + ". Open PEOPLE to join them!";
if (newlyOnlineConnectionsArray.length > 0) {
var message;
if (!ui.notificationInitialCallbackMade) {
message = newlyOnlineConnectionsArray.length + " of your connections " +
(newlyOnlineConnectionsArray.length === 1 ? "is" : "are") + " online! Open PEOPLE to join them.";
ui.notificationDisplayBanner(message);
} else {
for (i = 0; i < newlyOnlineConnectionsArray.length; i++) {
message = newlyOnlineConnectionsArray[i].username + " is available in " +
newlyOnlineConnectionsArray[i].location.root.name + "! Open PEOPLE to join them.";
ui.notificationDisplayBanner(message);
}
}
}
}
@ -902,7 +904,7 @@ function startup() {
onOpened: palOpened,
onClosed: off,
onMessage: fromQml,
notificationPollEndpoint: "/api/v1/users?filter=connections&per_page=10",
notificationPollEndpoint: "/api/v1/notifications?source=users&filter=connections&per_page=10",
notificationPollTimeoutMs: 60000,
notificationDataProcessPage: notificationDataProcessPage,
notificationPollCallback: notificationPollCallback,