Files
com_r35157_nenjim-hubd-impl…/openspec/specs/notification-services/spec.md
T

5.1 KiB

notification-services Specification

Purpose

Defines transport-independent notification services whose delivery configuration is bound before consumers submit semantically tagged text messages.

Requirements

Requirement: Transport-independent bound notification contract

The notification API SHALL provide a non-generic bound service under com.r35157.service.notification whose only delivery input is an ΩNotificationMessageΩ and whose synchronous failures use IOException. A consumer using an already bound service SHALL NOT need a transport-specific message type or an implementation-package dependency.

Scenario: Bound consumer sends a message

  • WHEN a consumer receives a configured BoundNotificationService
  • THEN it can call push(message) using only an ΩNotificationMessageΩ

Scenario: Delivery failure is reported synchronously

  • WHEN a bound transport encounters a delivery failure
  • THEN push(message) reports the failure through its IOException contract

Requirement: Addressed services bind destination configuration

The notification API SHALL provide an AddressedNotificationService generic only over a NotificationDestination type. Binding a destination SHALL produce a BoundNotificationService that captures the destination so later calls require only an ΩNotificationMessageΩ.

Scenario: Destination is bound once

  • WHEN a destination is passed to an addressed notification service's binding operation
  • THEN the returned bound service sends subsequent messages to that captured destination without requiring it again

Requirement: Notification message validation

Every public notification-service push(...) entry point SHALL reject a null, empty, or blank ΩNotificationMessageΩ with IllegalArgumentException before attempting any network or transport operation.

Scenario: Null message is rejected

  • WHEN a caller pushes a null notification message
  • THEN the service throws IllegalArgumentException before delivery is attempted

Scenario: Empty or blank message is rejected

  • WHEN a caller pushes an empty or whitespace-only notification message
  • THEN the service throws IllegalArgumentException before delivery is attempted

Requirement: Pushover delivery remains functional

The Pushover implementation SHALL accept ΩNotificationMessageΩ directly, preserve its existing synchronous HTTP delivery behavior, and expose it as PushoverNotificationService implementing BoundNotificationService.

Scenario: Valid Pushover message is submitted

  • WHEN a caller pushes a valid message through a configured Pushover notification service
  • THEN the service submits the same message through the existing Pushover API request flow

Scenario: Pushover rejects delivery

  • WHEN Pushover returns a non-successful HTTP response or communication fails
  • THEN the service reports the delivery failure as an IOException

Requirement: SMTP binding captures address and subject

An SMTP destination SHALL contain both an ΩEmailAddressΩ and a fixed ΩEmailSubjectΩ. SMTP SHALL support binding these two values into a BoundNotificationService, and SHALL reject a null, empty, or blank address or subject with IllegalArgumentException when the destination is created.

Scenario: SMTP service is fully bound

  • WHEN a caller binds a valid email address and subject
  • THEN the returned bound service requires only an ΩNotificationMessageΩ for each push

Scenario: Invalid SMTP binding is rejected

  • WHEN a caller creates or requests an SMTP binding with a null, empty, or blank email address or subject
  • THEN the operation throws IllegalArgumentException

Scenario: Valid SMTP delivery remains unimplemented

  • WHEN a valid message is pushed through a valid SMTP binding
  • THEN the service reports that SMTP delivery is not implemented

Requirement: Discord delivery remains unimplemented

The Discord stub SHALL implement BoundNotificationService, accept ΩNotificationMessageΩ directly, and SHALL NOT implement webhook delivery as part of this capability.

Scenario: Valid Discord delivery remains unimplemented

  • WHEN a valid message is pushed through the configured Discord service
  • THEN the service reports that Discord delivery is not implemented without performing webhook delivery

Requirement: Obsolete notification API is removed

The notification framework SHALL reside exclusively under com.r35157.service.notification. It SHALL NOT retain compatibility aliases under com.r35157.libs.notification, notifier-named public interfaces or implementations, the NotificationMessage marker, or transport-specific message wrapper types.

Scenario: Production code uses the new service API

  • WHEN the production source tree is inspected after migration
  • THEN notification framework code and consumers reference only the new package and service-oriented types

Scenario: Removed types are unavailable

  • WHEN downstream code attempts to import an old notifier or message-wrapper type
  • THEN that type is no longer part of the source or compiled API