Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix/cron downtime #47

Merged
merged 3 commits into from
Feb 9, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion snap/dist/bundle.js

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion snap/snap.manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
"url": "https://github.com/ethereum-push-notification-service/push-protocol-snaps"
},
"source": {
"shasum": "E92WYxVcFeu9gtJzbctpTdjxmBwVajf+4747fGIma6o=",
"shasum": "Qeij5+T2NeMuJ7Iv4l+vciRfSjoLUguxA9LAXeYhFVY=",
"location": {
"npm": {
"filePath": "dist/bundle.js",
Expand Down
3 changes: 2 additions & 1 deletion snap/src/config/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,5 +11,6 @@ export const BASE_URL = 'https://backend.epns.io/apis/v1'; // Modify this as nee

export const defaultLatestSnapState: LatestSnapState = {
version: 1,
addresses: {}
addresses: {},
pendingInAppNotifs: []
}
4 changes: 4 additions & 0 deletions snap/src/handlers/cronJobHandler.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { OnCronjobHandler } from "@metamask/snaps-types";
import { notifCronJob } from "../methods";
import { SnapCronJobMethod } from "../types";
import { getModifiedSnapState } from "../utils";

/**
* Handles cronjobs for the Snap, executing the appropriate method based on the request.
Expand All @@ -11,6 +12,9 @@ import { SnapCronJobMethod } from "../types";
*/
export const onCronjob: OnCronjobHandler = async ({ request }) => {
try {
// Just modify the state version
await getModifiedSnapState({ encrypted: false });

switch (request.method as SnapCronJobMethod) {
case SnapCronJobMethod.NotifCronJob:
await notifCronJob();
Expand Down
66 changes: 19 additions & 47 deletions snap/src/methods/cronJobs/notifCronJob.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
import { divider, heading, panel, text } from "@metamask/snaps-ui";
import {
fetchAllAddrNotifs,
getCurrentTimestamp,
getModifiedSnapState,
popupHelper,
notifyInMetamaskApp,
sleep,
updateSnapState,
} from "../../utils";

/**
Expand All @@ -17,69 +19,39 @@ export const notifCronJob = async (): Promise<void> => {
// Fetch notifications for all subscribed addresses
const notifs = await fetchAllAddrNotifs();

// Generate popup messages based on notifications
const msgs = popupHelper(notifs);

// Just modify the state version
await getModifiedSnapState({ encrypted: false });

// if user is receiving more than 25 notifications, then remind them to turn on snooze
// if (Number(popuptoggle) <= 15 && currentTimeEpoch > Number(persistedData.snoozeDuration)) {

// Display an alert for new notifications
if (msgs.length > 0) {
if (notifs.length > 0) {
await snap.request({
method: "snap_dialog",
params: {
type: "alert",
content: panel([
heading("You have a new notification!"),
divider(),
...msgs.map((msg) => text(msg)),
...notifs.map((notif) => text(notif.popupMsg)),
]),
},
});
}

// } else if (Number(popuptoggle) == 16 && currentTimeEpoch >= Number(persistedData.snoozeDuration)) {
// await SnapStorageCheck();

// const result = await snap.request({
// method: 'snap_dialog',
// params: {
// type: 'confirmation',
// content: panel([
// heading('Snooze Notifications'),
// divider(),
// text('Too many notifications to keep up with? You can temporarily snooze them to take a break. Approving will enable notification snooze.'),
// ]),
// },
// });
// Display in-app notifications
await notifyInMetamaskApp(notifs);

// if (result) {
// const snoozeDuration = await snoozeNotifs();
// setSnoozeDuration(Number(snoozeDuration));
// }
// break;
// }
const state = await getModifiedSnapState({ encrypted: false });
const currentTimeStamp = getCurrentTimestamp();

// Display in-app notifications
if (msgs.length > 0) {
const maxlength = msgs.length > 11 ? 11 : msgs.length;
for (let i = 0; i < maxlength; i++) {
let msg = msgs[i];
msg = String(msg);
msg = msg.slice(0, 47);
await snap.request({
method: "snap_notify",
params: {
type: "inApp",
message: msg,
},
});
await sleep(5000); // Wait for 5 seconds between notifications
// Iterate over addresses in state
for (const address in state.addresses) {
// Check if the address is enabled
if (state.addresses[address].enabled) {
// Update the lastFeedsProcessedTimestamp for enabled addresses
state.addresses[address].lastFeedsProcessedTimestamp = currentTimeStamp;
}
}
await updateSnapState({
newState: state,
encrypted: false
});
} catch (error) {
// Handle or log the error as needed
console.error("Error in notifCronJob:", error);
Expand Down
6 changes: 3 additions & 3 deletions snap/src/services/getFeeds.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { BASE_URL } from "../config";
import { fetchGet } from "../utils";

interface Payload {
export interface Payload {
data: {
app: string;
sid: string;
Expand All @@ -27,7 +27,7 @@ interface Payload {
verificationProof: string;
}

interface Feed {
export interface Feed {
payload_id: number;
sender: string;
epoch: string;
Expand All @@ -36,7 +36,7 @@ interface Feed {
etime: string | null;
}

interface IFeeds {
export interface IFeeds {
feeds: Feed[];
itemCount: number;
}
Expand Down
16 changes: 15 additions & 1 deletion snap/src/types/index.ts
Original file line number Diff line number Diff line change
@@ -1,2 +1,16 @@
export * from "./snapApi";
export * from "./snapState";
export * from "./snapState";

/**
* Represents a notification object format.
*/
export interface INotification {
address: string; // Address associated with the notification
timestamp: number; // Timestamp when the notification was received
notification: {
body: string; // Body content of the notification
title: string; // Title of the notification
};
popupMsg: string; // Message for displaying in a popup
inAppNotifMsg: string; // Message for displaying in an in-app notification of metamask
}
27 changes: 21 additions & 6 deletions snap/src/types/snapState.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ export type UnifiedSnapState = SnapStateV0 | SnapStateV1;

export type LatestSnapState = SnapStateV1;

// snap persisted state (non-encrypted) till v1.1.12
// snap persisted state (non-encrypted) till v1.1.12
export type SnapStateV0 = {
addresses: Array<string>;
popuptoggle: number;
Expand All @@ -13,13 +13,28 @@ export type SnapStateV0 = {

// snap persisted state (non-encrypted) from v1.1.13
export type SnapStateV1 = {
version: 1;
addresses: { [address: string]: AddressMetadata };
version: 1; // Represents version of state
addresses: { [address: string]: AddressMetadata }; // Map of addresses to their metadata
pendingInAppNotifs: NotificationMetaData[]; // Array of pending in-app notifications (notifs that are not added in metamask inApp notifs tab)
};

export type AddressMetadata = {
// @Purpose: Represents if the address is enabled to receive notifications.
// @Default: false
enabled: boolean;
// Add any other metadata fields you may need in future

// @Purpose: Represents the timestamp when the last cron job ran and processed feeds for this address.
// @Default: timestamp when address was added in snap
lastFeedsProcessedTimestamp: number;

// Add any other metadata fields you may need in the future
};

export type NotificationMetaData = {
address: string; // Unique identifier for the notification
message: string; // Message content of the notification
timestamp: number; // Timestamp when the notification was created
// Add more properties as needed
};

export interface ISnapStateParam {
Expand All @@ -30,6 +45,6 @@ export interface IUpdateSnapState extends ISnapStateParam {
newState: LatestSnapState;
}

export type IGetSnapState = ISnapStateParam
export type IGetSnapState = ISnapStateParam;

export type IGetModifiedSnapState = ISnapStateParam
export type IGetModifiedSnapState = ISnapStateParam;
18 changes: 10 additions & 8 deletions snap/src/utils/address.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,10 @@
import { divider, heading, panel, text } from "@metamask/snaps-ui";
import {
getModifiedSnapState,
updateSnapState,
} from "./snapStateUtils";
import { getModifiedSnapState, updateSnapState } from "./snapStateUtils";

import { ethers } from "ethers";
import { AddressMetadata, LatestSnapState } from "../types";
import { getEnabledAddresses } from "./helperFn";
import { getCurrentTimestamp } from "./time";

/**
* Handles the addition of an Ethereum address to the list of monitored addresses.
Expand All @@ -27,8 +25,12 @@ export const handleAddAddress = async (address: string) => {
* Otherwise, create a new metadata object with 'enabled' set to true.
*/
const updatedMetadata: AddressMetadata = metadata
? { ...metadata, enabled: true }
: { enabled: true };
? {
...metadata,
enabled: true,
lastFeedsProcessedTimestamp: getCurrentTimestamp(),
}
: { enabled: true, lastFeedsProcessedTimestamp: getCurrentTimestamp() };

// Create a new SnapStateV1 object with the updated metadata.

Expand Down Expand Up @@ -146,8 +148,8 @@ export const handleRemoveAddress = async (address: string) => {
* Otherwise, create a new metadata object with 'enabled' set to false.
*/
const updatedMetadata: AddressMetadata = metadata
? { ...metadata, enabled: false }
: { enabled: false };
? { ...metadata, enabled: false, lastFeedsProcessedTimestamp: 0 }
: { enabled: false, lastFeedsProcessedTimestamp: 0 };

//Create a new SnapStateV1 object with the updated metadata.

Expand Down
3 changes: 2 additions & 1 deletion snap/src/utils/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ export * from "./notifs";
export * from "./snapStateUtils";
// export * from "./snapstoragecheck";
// export * from "./snooze";
export * from "./toggle";
// export * from "./toggle";
export * from "./helperFn";
export * from "./api";
export * from "./time";
Loading