You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
315 lines
7.5 KiB
315 lines
7.5 KiB
/**
|
|
* NotificationContent.java
|
|
*
|
|
* Data model for notification content following the project directive schema
|
|
* Implements the canonical NotificationContent v1 structure
|
|
*
|
|
* @author Matthew Raymer
|
|
* @version 1.0.0
|
|
*/
|
|
|
|
package com.timesafari.dailynotification;
|
|
|
|
import java.util.UUID;
|
|
|
|
/**
|
|
* Represents notification content with all required fields
|
|
*
|
|
* This class follows the canonical schema defined in the project directive:
|
|
* - id: string (uuid)
|
|
* - title: string
|
|
* - body: string (plain text; may include simple emoji)
|
|
* - scheduledTime: epoch millis (client-local target)
|
|
* - mediaUrl: string? (for future; must be mirrored to local path before use)
|
|
* - fetchTime: epoch millis
|
|
*/
|
|
public class NotificationContent {
|
|
|
|
private String id;
|
|
private String title;
|
|
private String body;
|
|
private long scheduledTime;
|
|
private String mediaUrl;
|
|
private long fetchTime;
|
|
private boolean sound;
|
|
private String priority;
|
|
private String url;
|
|
|
|
/**
|
|
* Default constructor with auto-generated UUID
|
|
*/
|
|
public NotificationContent() {
|
|
this.id = UUID.randomUUID().toString();
|
|
this.fetchTime = System.currentTimeMillis();
|
|
this.sound = true;
|
|
this.priority = "default";
|
|
}
|
|
|
|
/**
|
|
* Constructor with all required fields
|
|
*
|
|
* @param title Notification title
|
|
* @param body Notification body text
|
|
* @param scheduledTime When to display the notification
|
|
*/
|
|
public NotificationContent(String title, String body, long scheduledTime) {
|
|
this();
|
|
this.title = title;
|
|
this.body = body;
|
|
this.scheduledTime = scheduledTime;
|
|
}
|
|
|
|
// Getters and Setters
|
|
|
|
/**
|
|
* Get the unique identifier for this notification
|
|
*
|
|
* @return UUID string
|
|
*/
|
|
public String getId() {
|
|
return id;
|
|
}
|
|
|
|
/**
|
|
* Set the unique identifier for this notification
|
|
*
|
|
* @param id UUID string
|
|
*/
|
|
public void setId(String id) {
|
|
this.id = id;
|
|
}
|
|
|
|
/**
|
|
* Get the notification title
|
|
*
|
|
* @return Title string
|
|
*/
|
|
public String getTitle() {
|
|
return title;
|
|
}
|
|
|
|
/**
|
|
* Set the notification title
|
|
*
|
|
* @param title Title string
|
|
*/
|
|
public void setTitle(String title) {
|
|
this.title = title;
|
|
}
|
|
|
|
/**
|
|
* Get the notification body text
|
|
*
|
|
* @return Body text string
|
|
*/
|
|
public String getBody() {
|
|
return body;
|
|
}
|
|
|
|
/**
|
|
* Set the notification body text
|
|
*
|
|
* @param body Body text string
|
|
*/
|
|
public void setBody(String body) {
|
|
this.body = body;
|
|
}
|
|
|
|
/**
|
|
* Get the scheduled time for this notification
|
|
*
|
|
* @return Timestamp in milliseconds
|
|
*/
|
|
public long getScheduledTime() {
|
|
return scheduledTime;
|
|
}
|
|
|
|
/**
|
|
* Set the scheduled time for this notification
|
|
*
|
|
* @param scheduledTime Timestamp in milliseconds
|
|
*/
|
|
public void setScheduledTime(long scheduledTime) {
|
|
this.scheduledTime = scheduledTime;
|
|
}
|
|
|
|
/**
|
|
* Get the media URL (optional, for future use)
|
|
*
|
|
* @return Media URL string or null
|
|
*/
|
|
public String getMediaUrl() {
|
|
return mediaUrl;
|
|
}
|
|
|
|
/**
|
|
* Set the media URL (optional, for future use)
|
|
*
|
|
* @param mediaUrl Media URL string or null
|
|
*/
|
|
public void setMediaUrl(String mediaUrl) {
|
|
this.mediaUrl = mediaUrl;
|
|
}
|
|
|
|
/**
|
|
* Get the fetch time when content was retrieved
|
|
*
|
|
* @return Timestamp in milliseconds
|
|
*/
|
|
public long getFetchTime() {
|
|
return fetchTime;
|
|
}
|
|
|
|
/**
|
|
* Set the fetch time when content was retrieved
|
|
*
|
|
* @param fetchTime Timestamp in milliseconds
|
|
*/
|
|
public void setFetchTime(long fetchTime) {
|
|
this.fetchTime = fetchTime;
|
|
}
|
|
|
|
/**
|
|
* Check if sound should be played
|
|
*
|
|
* @return true if sound is enabled
|
|
*/
|
|
public boolean isSound() {
|
|
return sound;
|
|
}
|
|
|
|
/**
|
|
* Set whether sound should be played
|
|
*
|
|
* @param sound true to enable sound
|
|
*/
|
|
public void setSound(boolean sound) {
|
|
this.sound = sound;
|
|
}
|
|
|
|
/**
|
|
* Get the notification priority
|
|
*
|
|
* @return Priority string (high, default, low)
|
|
*/
|
|
public String getPriority() {
|
|
return priority;
|
|
}
|
|
|
|
/**
|
|
* Set the notification priority
|
|
*
|
|
* @param priority Priority string (high, default, low)
|
|
*/
|
|
public void setPriority(String priority) {
|
|
this.priority = priority;
|
|
}
|
|
|
|
/**
|
|
* Get the associated URL
|
|
*
|
|
* @return URL string or null
|
|
*/
|
|
public String getUrl() {
|
|
return url;
|
|
}
|
|
|
|
/**
|
|
* Set the associated URL
|
|
*
|
|
* @param url URL string or null
|
|
*/
|
|
public void setUrl(String url) {
|
|
this.url = url;
|
|
}
|
|
|
|
/**
|
|
* Check if this notification is stale (older than 24 hours)
|
|
*
|
|
* @return true if notification is stale
|
|
*/
|
|
public boolean isStale() {
|
|
long currentTime = System.currentTimeMillis();
|
|
long age = currentTime - fetchTime;
|
|
return age > 24 * 60 * 60 * 1000; // 24 hours in milliseconds
|
|
}
|
|
|
|
/**
|
|
* Get the age of this notification in milliseconds
|
|
*
|
|
* @return Age in milliseconds
|
|
*/
|
|
public long getAge() {
|
|
return System.currentTimeMillis() - fetchTime;
|
|
}
|
|
|
|
/**
|
|
* Get the age of this notification in a human-readable format
|
|
*
|
|
* @return Human-readable age string
|
|
*/
|
|
public String getAgeString() {
|
|
long age = getAge();
|
|
long seconds = age / 1000;
|
|
long minutes = seconds / 60;
|
|
long hours = minutes / 60;
|
|
long days = hours / 24;
|
|
|
|
if (days > 0) {
|
|
return days + " day" + (days == 1 ? "" : "s") + " ago";
|
|
} else if (hours > 0) {
|
|
return hours + " hour" + (hours == 1 ? "" : "s") + " ago";
|
|
} else if (minutes > 0) {
|
|
return minutes + " minute" + (minutes == 1 ? "" : "s") + " ago";
|
|
} else {
|
|
return "just now";
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Check if this notification is ready to be displayed
|
|
*
|
|
* @return true if notification should be displayed now
|
|
*/
|
|
public boolean isReadyToDisplay() {
|
|
return System.currentTimeMillis() >= scheduledTime;
|
|
}
|
|
|
|
/**
|
|
* Get time until this notification should be displayed
|
|
*
|
|
* @return Time in milliseconds until display
|
|
*/
|
|
public long getTimeUntilDisplay() {
|
|
return Math.max(0, scheduledTime - System.currentTimeMillis());
|
|
}
|
|
|
|
@Override
|
|
public String toString() {
|
|
return "NotificationContent{" +
|
|
"id='" + id + '\'' +
|
|
", title='" + title + '\'' +
|
|
", body='" + body + '\'' +
|
|
", scheduledTime=" + scheduledTime +
|
|
", mediaUrl='" + mediaUrl + '\'' +
|
|
", fetchTime=" + fetchTime +
|
|
", sound=" + sound +
|
|
", priority='" + priority + '\'' +
|
|
", url='" + url + '\'' +
|
|
'}';
|
|
}
|
|
|
|
@Override
|
|
public boolean equals(Object o) {
|
|
if (this == o) return true;
|
|
if (o == null || getClass() != o.getClass()) return false;
|
|
|
|
NotificationContent that = (NotificationContent) o;
|
|
return id.equals(that.id);
|
|
}
|
|
|
|
@Override
|
|
public int hashCode() {
|
|
return id.hashCode();
|
|
}
|
|
}
|
|
|