## Purpose

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

## ADDED 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
