Skip to content

Self-Hosted Notification System using ntfy in a Docker ​

(with Example Notification for Order Received)

Notification System Diagram ​

uml diagram

Components ​

  • Shopping Cart System: Sends transaction data via webhooks.
  • Make Scenario: Processes incoming webhooks and filters transactions.
  • Ntfy Server: Hosted in a fly.io Docker container—handles receiving and sending notifications.

Order Received Identification ​

A filter in the Make scenario checks the transaction data bundle received from the Shopping Cart, allowing the scenario to proceed only if specified conditions are met.

Ntfy Server ​

  • Service URL: your-ntfy-app.fly.dev
  • Subscribe Topic: order_received
  • Full Ntfy Order Received URL: https://your-ntfy-app.fly.dev/order_received
  • User: username (read-write access to order_received topic)
  • Password: password

For more information, refer to the ntfy documentation on your server: https://your-ntfy-app.fly.dev/docs/

Setting Up Users and Permissions ​

To set up users and manage their permissions via the ntfy service, change to your ntfy app directory, and follow these steps in the Fly console:

  1. Access the Fly Console:

    bash
    fly ssh console -a your-ntfy-app
  2. Add a User:

    bash
    ntfy user add <username>
  3. Set User Password:

    bash
    ntfy user set-password <username> <password>
  4. Configure User Permissions:

    To grant read-write access to a topic, execute:

    bash
    ntfy user set-access <username> <topic> rw

Using ntfy Username and Password in Make Scenario ​

When the Make scenario's HTTP Module invokes the ntfy endpoint to publish a message to the order_received topic, it must authenticate using the ntfy username and password.

  • HTTP Request Setup:
    • URL: https://your-ntfy-app.fly.dev/order_received
    • Method: POST
    • Headers:
      • Authorization: Basic <base64_encoded_credentials>
        • The credentials are encoded in base64 format: username:password (Use an online tool for encoding a string to base64 format, such as Base64 Encode - Base64 Converter)

Deploying and Managing the Fly Machine ​

Navigate to your ntfy development folder, where the fly.toml file is located.

  • Deploy app:
    bash
    fly deploy
  • Start app:
    bash
    fly launch
  • Check the status of your machine(s):
    bash
    fly status
  • Monitor logs for errors or warnings:
    bash
    fly logs
  • Restart ntfy server:
    bash
    fly apps restart your-ntfy-app

Using Your ntfy Service ​

Via ntfy app on Android or iPhone:

  • In Settings, change Default server to https://your-ntfy-app.fly.dev
  • Add user username, password password
  • Subscribe to topic order_received
  • Set app notifications (optional)

Via browser link: https://your-ntfy-app.fly.dev:

  • Sign in as username, with password password
  • Subscribe to topic order_received
  • Set browser notifications (optional)

Note: If user username has write permission to the topic order_received, you will be able to publish messages to that topic from the client.

More info about using ntfy: https://your-ntfy-app.fly.dev/docs/ on your machine, or at ntfy.sh.

Reference: Ntfy Config ​

server.yml ​

auth-default-access: "deny-all" ensures that topics cannot be read nor published to without authentication and proper read or write authorization.

yaml
base-url: "https://your-ntfy-app.fly.dev"
listen-http: ":80"
cache-file: "/data/cache.db"
attachment-cache-dir: "/data/attachments/"
auth-file: "/data/user.db"
auth-default-access: "deny-all"

fly.toml ​

Note: If auto_stop_machines is true (or 'stop') and auto_start_machines is true, ensure the min_machines_running setting is not 0, as your ntfy server could stop without restarting.

toml
#
# See https://fly.io/docs/reference/configuration/ for information about how to use this file.
#

app = 'your-ntfy-app'
primary_region = 'sea'

[build]

[[mounts]]
  source = 'ntfy_data'
  destination = '/data'

[http_service]
  internal_port = 80
  force_https = true
  auto_stop_machines = 'stop'
  auto_start_machines = true
  min_machines_running = 1
  processes = ['app']

[[services]]
  protocol = 'tcp'
  internal_port = 80

  [[services.ports]]
    port = 80
    handlers = ['http']

  [[services.ports]]
    port = 443
    handlers = ['tls', 'http']

[[vm]]
  memory = '1gb'
  cpu_kind = 'shared'
  cpus = 1

Dockerfile ​

dockerfile
FROM binwiederhier/ntfy
COPY server.yml /etc/ntfy/server.yml
ENTRYPOINT ["ntfy", "serve"]

#Ntfy #NtfyServer #Webhooks
#Docker #FlyDev