Docs / API

API Reference

All exports from @ambersecurityinc/notifly.

notify()

Send a notification to one or more services simultaneously.

signature
function notify(
  options: NotiflyOptions,
  message: NotiflyMessage,
): Promise<NotiflyResult[]>

Parameters

Parameter Type Description
options NotiflyOptions Object containing the urls array
options.urls string[] List of notification URLs (one per service)
message NotiflyMessage The notification content to send
message.body string Main notification text (required)
message.title string Notification title (optional)
message.type 'info' | 'success' | 'warning' | 'failure' Message severity level (optional, default: 'info')

Returns

A Promise that resolves to an array of NotiflyResult objects — one per URL, in order. The promise always resolves (never rejects), even if some services fail. Uses Promise.allSettled internally for full concurrency.

NotiflyResult
interface NotiflyResult {
  success: boolean;
  service: string;  // e.g. 'discord', 'ntfy'
  error?: string;   // present only when success is false
}

Example

example
import { notify } from '@ambersecurityinc/notifly';

const results = await notify(
  {
    urls: [
      'discord://1234567890/token',
      'ntfy://my-topic',
      'invalid-url',  // gracefully handled
    ],
  },
  { title: 'Deploy', body: 'v2.0 is live', type: 'success' }
);

for (const result of results) {
  if (!result.success) {
    console.error(`${result.service}: ${result.error}`);
  }
}

parseUrl()

Parse a notification URL string into a service config object.

signature
function parseUrl(url: string): ServiceConfig

Throws a ParseError if the URL scheme is unknown or the URL is malformed.

example
import { parseUrl, ParseError } from '@ambersecurityinc/notifly';

try {
  const config = parseUrl('discord://1234567890/mytoken');
  console.log(config);
  // { service: 'discord', webhook_id: '1234567890', webhook_token: 'mytoken' }
} catch (err) {
  if (err instanceof ParseError) {
    console.error('Bad URL:', err.message);
  }
}

registerService()

Register a custom notification service plugin.

signature
function registerService(definition: ServiceDefinition): void
ServiceDefinition
interface ServiceDefinition {
  schemas: string[];
  parseUrl(url: URL): ServiceConfig;
  send(config: ServiceConfig, message: NotiflyMessage): Promise<NotiflyResult>;
}

See the Custom Services guide for a full walkthrough.

example
import { registerService, notify } from '@ambersecurityinc/notifly';

registerService({
  schemas: ['myapp'],
  parseUrl(url) {
    return { service: 'myapp', token: url.hostname };
  },
  async send(config, message) {
    const res = await fetch('https://api.myapp.com/notify', {
      method: 'POST',
      headers: { Authorization: `Bearer ${config.token}` },
      body: JSON.stringify({ text: message.body }),
    });
    return { success: res.ok, service: 'myapp' };
  },
});

// Now usable via notify()
await notify({ urls: ['myapp://my-token'] }, { body: 'Hello!' });

Type Reference

NotiflyMessage

typescript
interface NotiflyMessage {
  title?: string;
  body: string;
  type?: 'info' | 'success' | 'warning' | 'failure';
}

NotiflyResult

typescript
interface NotiflyResult {
  success: boolean;
  service: string;
  error?: string;
}

NotiflyOptions

typescript
interface NotiflyOptions {
  urls: string[];
}

ServiceConfig

typescript
interface ServiceConfig {
  service: string;
  [key: string]: unknown;
}

ServiceDefinition

typescript
interface ServiceDefinition {
  schemas: string[];
  parseUrl(url: URL): ServiceConfig;
  send(config: ServiceConfig, message: NotiflyMessage): Promise<NotiflyResult>;
}

ParseError

typescript
class ParseError extends Error {
  name: 'ParseError';
}

ServiceError

typescript
class ServiceError extends Error {
  name: 'ServiceError';
  status: number;   // HTTP status code from the service
  body: string;     // Raw response body
}
← Previous Installation Next → Services Overview