Skip to content

Commit f966b2f

Browse files
author
Philipp Heckel
committedDec 9, 2021
Add 'Firebase: no' header, closes #42
1 parent d6fbcca commit f966b2f

File tree

3 files changed

+88
-14
lines changed

3 files changed

+88
-14
lines changed
 

‎docs/examples.md

+10-1
Original file line numberDiff line numberDiff line change
@@ -64,5 +64,14 @@ It looked something like this:
6464
curl -d "$(hostname),$count,$time" ntfy.sh/results
6565
```
6666

67+
## Ansible, Salt and Puppet
68+
You can easily integrate ntfy into Ansible, Salt, or Puppet to notify you when runs are done or are highstated.
69+
One of my co-workers uses the following Ansible task to let him know when things are done:
6770

68-
71+
```yml
72+
- name: Send ntfy.sh update
73+
uri:
74+
url: "https://ntfy.sh/{{ ntfy_channel }}"
75+
method: POST
76+
body: "{{ inventory_hostname }} reseeding complete"
77+
```

‎docs/publish.md

+66-1
Original file line numberDiff line numberDiff line change
@@ -332,7 +332,14 @@ them with a comma, e.g. `tag1,tag2,tag3`.
332332
<figcaption>Detail view of notifications with tags</figcaption>
333333
</figure>
334334

335-
## Message caching
335+
## Advanced features
336+
337+
### Message caching
338+
!!! info
339+
If `Cache: no` is used, messages will only be delivered to connected subscribers, and won't be re-delivered if a
340+
client re-connects. If a subscriber has (temporary) network issues or is reconnecting momentarily,
341+
**messages might be missed**.
342+
336343
By default, the ntfy server caches messages on disk for 12 hours (see [message caching](config.md#message-cache)), so
337344
all messages you publish are stored server-side for a little while. The reason for this is to overcome temporary
338345
client-side network disruptions, but arguably this feature also may raise privacy concerns.
@@ -385,3 +392,61 @@ are still delivered to connected subscribers, but [`since=`](subscribe/api.md#fe
385392
]
386393
]));
387394
```
395+
396+
### Firebase
397+
!!! info
398+
If `Firebase: no` is used and [instant delivery](subscribe/phone.md#instant-delivery) isn't enabled in the Android
399+
app (Google Play variant only), **message delivery will be significantly delayed (up to 15 minutes)**. To overcome
400+
this delay, simply enable instant delivery.
401+
402+
The ntfy server can be configured to use [Firebase Cloud Messaging (FCM)](https://firebase.google.com/docs/cloud-messaging)
403+
(see [Firebase config](config.md#firebase-fcm)) for message delivery on Android (to minimize the app's battery footprint).
404+
The ntfy.sh server is configured this way, meaning that all messages published to ntfy.sh are also published to corresponding
405+
FCM topics.
406+
407+
If you'd like to avoid forwarding messages to Firebase, you can set the `X-Firebase` header (or its alias: `Firebase`)
408+
to `no`. This will instruct the server not to forward messages to Firebase.
409+
410+
=== "Command line (curl)"
411+
```
412+
curl -H "X-Firebase: no" -d "This message won't be forwarded to FCM" ntfy.sh/mytopic
413+
curl -H "Firebase: no" -d "This message won't be forwarded to FCM" ntfy.sh/mytopic
414+
```
415+
416+
=== "HTTP"
417+
``` http
418+
POST /mytopic HTTP/1.1
419+
Host: ntfy.sh
420+
Firebase: no
421+
422+
This message won't be forwarded to FCM
423+
```
424+
425+
=== "JavaScript"
426+
``` javascript
427+
fetch('https://ntfy.sh/mytopic', {
428+
method: 'POST',
429+
body: 'This message won't be forwarded to FCM',
430+
headers: { 'Firebase': 'no' }
431+
})
432+
```
433+
434+
=== "Go"
435+
``` go
436+
req, _ := http.NewRequest("POST", "https://ntfy.sh/mytopic", strings.NewReader("This message won't be forwarded to FCM"))
437+
req.Header.Set("Firebase", "no")
438+
http.DefaultClient.Do(req)
439+
```
440+
441+
=== "PHP"
442+
``` php-inline
443+
file_get_contents('https://ntfy.sh/mytopic', false, stream_context_create([
444+
'http' => [
445+
'method' => 'POST',
446+
'header' =>
447+
"Content-Type: text/plain\r\n" .
448+
"Firebase: no",
449+
'content' => 'This message won't be stored server-side'
450+
]
451+
]));
452+
```

‎server/server.go

+12-12
Original file line numberDiff line numberDiff line change
@@ -128,11 +128,6 @@ func New(conf *config.Config) (*Server, error) {
128128
if err != nil {
129129
return nil, err
130130
}
131-
for _, t := range topics {
132-
if firebaseSubscriber != nil {
133-
t.Subscribe(firebaseSubscriber)
134-
}
135-
}
136131
return &Server{
137132
config: conf,
138133
cache: cache,
@@ -284,13 +279,20 @@ func (s *Server) handlePublish(w http.ResponseWriter, r *http.Request, _ *visito
284279
if m.Message == "" {
285280
return errHTTPBadRequest
286281
}
287-
title, priority, tags, cache := parseHeaders(r.Header)
282+
title, priority, tags, cache, firebase := parseHeaders(r.Header)
288283
m.Title = title
289284
m.Priority = priority
290285
m.Tags = tags
291286
if err := t.Publish(m); err != nil {
292287
return err
293288
}
289+
if s.firebase != nil && firebase {
290+
go func() {
291+
if err := s.firebase(m); err != nil {
292+
log.Printf("Unable to publish to Firebase: %v", err.Error())
293+
}
294+
}()
295+
}
294296
if cache {
295297
if err := s.cache.AddMessage(m); err != nil {
296298
return err
@@ -306,7 +308,7 @@ func (s *Server) handlePublish(w http.ResponseWriter, r *http.Request, _ *visito
306308
return nil
307309
}
308310

309-
func parseHeaders(header http.Header) (title string, priority int, tags []string, cache bool) {
311+
func parseHeaders(header http.Header) (title string, priority int, tags []string, cache bool, firebase bool) {
310312
title = readHeader(header, "x-title", "title", "ti", "t")
311313
priorityStr := readHeader(header, "x-priority", "priority", "prio", "p")
312314
if priorityStr != "" {
@@ -333,7 +335,8 @@ func parseHeaders(header http.Header) (title string, priority int, tags []string
333335
}
334336
}
335337
cache = readHeader(header, "x-cache", "cache") != "no"
336-
return title, priority, tags, cache
338+
firebase = readHeader(header, "x-firebase", "firebase") != "no"
339+
return title, priority, tags, cache, firebase
337340
}
338341

339342
func readHeader(header http.Header, names ...string) string {
@@ -512,9 +515,6 @@ func (s *Server) topicsFromIDs(ids ...string) ([]*topic, error) {
512515
return nil, errHTTPTooManyRequests
513516
}
514517
s.topics[id] = newTopic(id)
515-
if s.firebase != nil {
516-
s.topics[id].Subscribe(s.firebase)
517-
}
518518
}
519519
topics = append(topics, s.topics[id])
520520
}
@@ -547,7 +547,7 @@ func (s *Server) updateStatsAndExpire() {
547547
log.Printf("cannot get stats for topic %s: %s", t.ID, err.Error())
548548
continue
549549
}
550-
if msgs == 0 && (subs == 0 || (s.firebase != nil && subs == 1)) { // Firebase is a subscriber!
550+
if msgs == 0 && subs == 0 {
551551
delete(s.topics, t.ID)
552552
continue
553553
}

0 commit comments

Comments
 (0)
Failed to load comments.