w3c/badging

Consider adding a getter

markcellus opened this issue · 3 comments

I've created this issue which was spawned from a discussion on #16 (comment). The current proposal explainer says:

The Badge interface is a member object on Window and Worker. It contains two methods:

  • void set(optional USVString or long): Sets the associated app's badge to the given data, or just "flag" if the argument is not given.
  • void clear(): Sets the associated app's badge to nothing.

These can be called from either a foreground page or a service worker (in either case, affecting the whole app, not just the current page).

It seems a little incomplete for the API to have a setter but no way to get badge counts for cases where there are multiple badge setters throughout an application that don't know about each other.

Let's say I have an application that shows both a chat box and email in the same interface. It gets one new unread chat message and shows 1 as badge count and then gets 2 new unread emails.

How would the application know that there was a badge count of one before it adds a 2 to that number? Sure, I could always query or listen in on both the chat message unread number and the email unread numbers, calculate them together and then call set() with the total number, but that would quickly become unwieldy. Then I would probably have to store both the chat unreads and email unreads on a globally accessible object (perhaps window) to make it available to both chat and email logic which breaks encapsulation. Why not avoid having to do this and just allow getting the badge number easily?

I'm not super keen on having a getter.

  • The badge could be used as a persistent cookie. Presumably a malicious site could do something similar with local storage, but it's still worth thinking about.

  • My intuition is that sites would probably have to recalculate the badge count between page loads anyway (as the data in the badge is almost certainly stale).

  • It could introduce strange behavior:
    Consider the case where you have two tabs open for the same site. Both sites receive a new message and increment the badge count. Only one message was received but the badge count was incremented by two.

    Explicitly setting the badge count to the unread count avoids this.

I'm not convinced that something like

Badge.increment();
// or
Badge.set(Badge.get() + 1);

is much better than

// Note: This also handles the unread count being reduced.
Badge.set(getUnreadCount());

Also, if you don't want to attach an unreadCount to window perhaps you could do it on the Badge global?

// On page load, use sophisticated algorithm to determine number of unread messages.
Badge.unreadCount = 7;
// Make sure the badge shows the right count.
Badge.set(Badge.unreadCount);

// Increment can be used to add one to the badge count.
Badge.increment = () => {
    Badge.unreadCount += 1;
    Badge.set(Badge.unreadCount);
};

(though note that the above could get out of sync between tabs. A better solution might do some kind of synchronization to try and avoid this).

Agree with @fallaciousreasoning‘s, um, reasoning. I also think we should leave the count management to the web application.