RSS News reader
RSS Reader
| System | AWTRIX NG Scripts |
|---|---|
| Firmware | AWTRIX NG |
| Topic | Social |
| Built by | strusic |
| File | 4MvrZml3vCYu.ax · 3.8 KB |
| Icons | 1 |
| Published | 26 Aug 2026 · updated 29 Aug 2026 |
| Downloads | 50 |
A background script for AWTRIX NG that monitors any public RSS feed and automatically triggers a notification on your matrix display whenever a brand-new article or headline appears.
🚀 What it does
Runs quietly in the background (Headless mode) without taking up a permanent slot in your app rotation.
Periodically fetches and parses XML/RSS feeds directly on the device.
Automatically cleans up titles (stripping out CDATA wrappers).
Triggers a notification popup only when a new headline is detected, complete with scroll speed, repeat count, and sound alerts.
⚙️ Requirements & Configuration
No external servers or Home Assistant automations are required—everything runs natively via Berry on your AWTRIX device. Once installed, you can configure the following parameters directly from the AWTRIX web interface (Apps -> Settings):
url: The target RSS feed link (default is set to RMF24 news feed - I was testing it on this feed).
icon: The icon ID displayed alongside the notification (default: 85).
speed: Scrolling speed percentage (range: 50–200).
repeat: Number of times the headline scrolls across the screen (range: 1–5).
sound: Notification sound effect (e.g., doorbell).
every: Check interval in minutes (range: 1–60 min).
UPDATE 29/08/26
- Removed Unsupported Functions: Eliminated the
.split()method from the text replacement logic, as it caused script crashes on the heavily restricted AWTRIX Berry engine. - Native String Slicing: Completely rewrote the custom
replace_stringfunction. It now uses a manual, character-by-character string slicing loop instead of relying on missing system methods. - Crash Prevention: Ensures multi-byte characters (like Polish typographic quotes
„and”) are safely and successfully converted to standard quotes (") using pure mathematical array indexing.
4MvrZml3vCYu.ax
# @name RSS Reader
# @desc Powiadamia o nowym tytule z kanału RSS (Headless)
# @author strusic
# @headless true
# @version 2.7
# @config url text "Adres RSS" default="https://www.rmf24.pl/fakty/feed"
# @config icon text "Ikona" default="85"
# @config speed number "Prędkość scroll" default=100 min=50 max=200 step=10
# @config repeat number "Ilość powtórzeń" default=2 min=1 max=5
# @config sound text "Dźwięk" default="doorbell"
# @config every number "Interwał (min)" default=15 min=1 max=60 unit=min
class RSSReader
var url, icon_name, sound_name, period, speed, repeat
var title
var ticks, in_flight
def init()
self.url = store.get("url")
self.icon_name = store.get("icon")
self.sound_name = store.get("sound")
self.speed = store.get("speed")
self.repeat = store.get("repeat")
self.period = store.get("every") * 60
self.title = store.get("title")
if self.title == nil
self.title = ""
end
self.ticks = 0
self.in_flight = false
log("RSSReader zainicjalizowany dla: " + str(self.url))
end
# Całkowicie natywna funkcja podmieniająca - bez split, tr czy replace
def replace_string(s, old, new)
var res = ""
var i = 0
var old_len = size(old)
var s_len = size(s)
if old_len == 0 return s end
# Skanujemy tekst szukając wycinka pasującego do "old"
while i <= s_len - old_len
if s[i .. i + old_len - 1] == old
res += new
i += old_len
else
res += s[i .. i]
i += 1
end
end
# Doklejamy resztę, jeśli coś zostało
while i < s_len
res += s[i .. i]
i += 1
end
return res
end
def on_body(body, status)
self.in_flight = false
if body == nil
log("RSSReader: Błąd pobierania danych, status: " + str(status))
return
end
var m = re.search("<title>(.*?)</title>", body)
if m == nil
log("RSSReader: Nie znaleziono znacznika title")
return
end
var raw_title = m[1]
# Oczyszczanie z tagów CDATA, jeśli występują
var cdata_m = re.search("<!\\[CDATA\\[(.*?)\\]\\]>", raw_title)
if cdata_m != nil
raw_title = cdata_m[1]
end
# Zamiana polskich cudzysłowów na standardowe
raw_title = self.replace_string(raw_title, "„", "\"")
raw_title = self.replace_string(raw_title, "”", "\"")
if raw_title != self.title
log("RSSReader: Nowy tytuł! Wyzwalam powiadomienie.")
self.title = raw_title
store.set("title", raw_title)
var spec = {
"text": self.title,
"icon": self.icon_name,
"repeat": self.repeat,
"scroll": { "speed": self.speed, "holdMs": 1500 }
}
if self.sound_name != ""
spec["sound"] = self.sound_name
end
notify(spec)
else
log("RSSReader: Tytuł bez zmian - czekam na kolejny cykl.")
end
end
def loop()
if self.ticks <= 0
self.ticks = self.period
if !self.in_flight
self.in_flight = true
http.get(self.url, / b, st -> self.on_body(b, st), {'find': "<item>", 'keep': 512})
end
end
self.ticks -= 1
end
end
return RSSReader()
Install it on your AWTRIX NG
Your browser writes the script straight to the device on your network. It joins the app rotation right away.
Some browsers refuse to talk to a device on your network from a public page. Download the flow and paste it into the Scripts tab of your device, or install it from a terminal:
These icons belong on the device, in /ICONS. Each one is at
most 32×8
pixels — shown here magnified, at their real proportions.
8×8 px
More flows for AWTRIX NG Scripts or Social
Something wrong with this flow? Report it.