Limerino

Limerino Privacy Policy

Last updated

Limerino is a native iOS Twitch chat client. This document describes exactly what data the app handles, where it lives, and who it is shared with.

If anything below is unclear or you'd like a copy of your data, contact hello@meipath.com.

TL;DR

  • Limerino has no analytics, no advertising SDKs, and no trackers. It uploads nothing about you or your activity except in situations you start yourself: signing in with Twitch, which establishes your mention-alerts session (see below); turning on mention alerts (same section); and sending feedback from Settings — Report a Bug or Suggest a Feature — both described under Bug reports & feature suggestions. The Limerino-operated endpoints it touches are a small sign-in bounce page (limerino.com/oauth/callback) and the backend at api.limerino.com. The bounce page belongs to the app's legacy web sign-in path; the current sign-in doesn't open it, and if that path ever runs, the token rides the URL fragment, which that server never receives (see Twitch authentication). The backend is contacted when you sign in, while mention alerts are on (see Mention alerts & Mention Vault), or when you send feedback — a bug report or a feature suggestion (see Bug reports & feature suggestions). Reporting objectionable chat is handled by Twitch — the in-app Report action opens Twitch's own report flow, and Limerino keeps no copy of reports (see Reporting below).
  • Signed-out mode preserves saved channel tabs and messages on your device. Limerino makes no Twitch chat connection until you sign in. Public global-emote catalogs from 7TV, BetterTTV, and FrankerFaceZ can still load at app start; the exact destinations and data sent appear in the network table below.
  • Signing in stores your Twitch login and tokens (access + refresh) in the device Keychain so the app can send chat, fetch your follows, use moderator tools, and keep you signed in between launches. Tokens never leave the device except to talk to Twitch's own APIs — and the identity check that establishes your mention-alerts session, described under Mention alerts & Mention Vault.
  • Limerino cannot delete data that Twitch holds. Limerino is a third-party Twitch client: your Twitch account, the messages you send, your follows, and your watch activity live on Twitch's servers under Twitch's own privacy policy. Deleting your Limerino data removes nothing from Twitch — use Twitch's own controls for that (see Removing your data).
  • Chat history for every channel you open is appended to a per-channel JSONL file under the app's Documents folder so you can scroll back. It never leaves the device.
  • When you're signed in, your Twitch whispers (DMs) and your mentions / highlights Inbox are saved on the device so they survive a relaunch. They are owner-scoped, never shared between accounts, and never uploaded. Clear them in the app, or uninstall, to delete them; signing out hides them but keeps each account's saved copy on the device for when you sign back in (see Removing your data).
  • After you sign in, scrollback from before you joined a channel can be fetched from recent-messages.robotty.de (a third-party, public API). You can turn it off in Settings.
  • Sharing, widgets, and Siri stay on your device. Channels you share into Limerino, pin to a home-screen widget / Live Activity, or open via the Siri shortcut are passed between Limerino's own app extensions and the main app through a private on-device container — nothing is uploaded.
  • Bug reports and feature suggestions are optional, user-initiated uploads. The policy below lists the exact text, device metadata, optional diagnostics, and server-side processors involved.

What Limerino collects, where it lives, and why

Twitch authentication (only when you sign in)

When you tap Sign in with Twitch in Settings → Account, the app starts Twitch's device-code flow: it shows you a short code and opens Twitch's own activation page (www.twitch.tv/activate) in a secure in-app web view (WKWebView). If that page needs you to sign in, it routes through Twitch's own login page (www.twitch.tv/login) — you enter your credentials on Twitch's pages, not in Limerino. You can approve in your system browser instead (Use browser instead — the path passkey sign-ins need). On success Twitch returns:

  • your Twitch login (username) and user-ID
  • an OAuth access token with the scopes you granted
  • a refresh token, which lets the app renew the access token so you stay signed in without repeating the login

Per signed-in account, the Keychain holds: the access token, the refresh token, your login, the granted scopes, the token expiry, and a pointer to which stored account is currently active. All of it lives in the iOS Keychain with kSecAttrAccessibleAfterFirstUnlockThisDeviceOnly, scoped to this device, non-syncing. The tokens are sent only to Twitch's official APIs (api.twitch.tv, id.twitch.tv, eventsub.wss.twitch.tv, irc.chat.twitch.tv) — with one exception you opt into by signing in: when the app establishes your mention-alerts session, the access token is also sent to api.limerino.com, where the server checks it against Twitch to confirm who you are, then discards it. It is never stored (see Mention alerts & Mention Vault).

The in-app approval page shares its web storage with the in-app video player, so the one Twitch login you perform there also signs the video player in. That player session is a Twitch web session cookie: a separate credential issued and controlled by Twitch, stored in the player's WebKit website storage on this device, never in Limerino's own storage. It is sent only to Twitch — to Twitch's web pages the way any browser cookie is, and once per established player session to Twitch's own token-check endpoint (id.twitch.tv), which is how the app verifies that the player's session belongs to the same Twitch account you signed into. The session is labeled unverified when that check cannot complete, and cleared if it provably belongs to a different account. Limerino never writes the cookie's value into logs, reports, or its own storage.

Every sign-in — including Sign in again for new features and adding another account — uses this same device-code flow; no OAuth redirect is involved. The app also keeps a small Limerino-operated bounce page registered as its OAuth redirect at https://limerino.com/oauth/callback (a static page on a Railway service, Cloudflare-fronted) for its legacy web sign-in path, which the current sign-in flow does not open. If that path runs, its only job is to forward the result back to the app's limerino://oauth/callback scheme; the access token travels in the URL fragment (the part after #), which browsers keep client-side and do not send to the server — so the page returns the sign-in to the app without the limerino.com server receiving your token. It runs no analytics and sets no cookies of its own.

To remove: Sign out (which also clears the video player's Twitch web session), or uninstall the app — see Removing your data below.

Chat logs (Documents/Limerino/Logs/)

Every channel you open writes its chat to <Documents>/Limerino/Logs/<channel>.jsonl. Each line records the message ID, sender login, display name, body, and timestamp. This is local-only — the file never leaves the device.

To remove: Uninstall the app — see Removing your data below.

Open channels and settings (SwiftData)

Your open channel tabs, custom commands, mod actions, blocked users, muted phrases, theme choice, and other preferences are persisted via SwiftData in the app's sandbox. Local-only.

To remove: Uninstall the app — see Removing your data below.

Whispers / direct messages (SwiftData, only when you're signed in)

When you are signed in, the Twitch whispers (direct messages) you send and receive through Limerino are saved to a private, owner-scoped SwiftData store on the device, so your conversations are still there when you relaunch. They are keyed to your Twitch user-ID, are never shared between accounts, and never leave the device except as the whisper itself travels over Twitch's own API.

To remove: Whispers → Clear deletes them from the device, as does uninstalling the app. Signing out hides them and stops new ones, but keeps this account's saved whispers on the device for when you sign back in — use Clear or uninstall to delete them. (See Removing your data.)

Mentions & highlights Inbox (SwiftData, only when you're signed in)

The Inbox collects messages that mention you or match your highlight rules so you can find them later. Each saved entry — the message text, who sent it, the channel, and a timestamp — is written to a private, owner-scoped SwiftData store on the device, capped to a recent window. It is local-only and never uploaded.

To remove: Clear it from the Inbox to delete the saved entries, or uninstall the app. Signing out hides the Inbox but keeps this account's saved entries on the device for next sign-in — use Clear or uninstall to delete them.

Mention alerts & Mention Vault

Mention alerts and the Mention Vault are the app's server-side features, served by the Limerino backend (api.limerino.com, hosted on Railway). Two different things reach that server, at two different times.

When you sign in, the app establishes your mention-alerts session, whether or not you use mention alerts. Your Twitch access token is sent to the server, which checks it against Twitch to confirm who you are and then discards it — it is never stored. The server keeps an identity row for you (your Twitch user-ID, login and display name, and your mention-alert entitlement state) and, so mention alerts can work, watches public Twitch chat across the channels our monitoring network covers for messages that mention your username. Each match is stored server-side in your Mention Vault so an alert can reach you even when Limerino isn't open:

  • Mention Vault — the message text, the channel, the chatter's public Twitch login/display name, and a timestamp, for each message that mentions you.
  • Blocked-user sync (optional) — if you use Twitch's block list, your blocked-user IDs can be synced to the server so a blocked chatter never generates a match or a vault entry.
  • Followed-channel list — once you open Notification settings or turn on mention alerts, the server stores the login names of the Twitch channels you follow (synced from your device), so alerts default to the channels you actually watch.
  • Notification preferences — your per-channel alert toggles, same-sender cooldown, batch window, quiet hours and time zone, and delivery mode (real-time or summary), so the server knows which pushes to send and when.

Sign in and that identity row and vault exist — they are what Retention below and Removing your data cover.

Turning mention alerts on registers this device to receive those alerts: it stores this device's APNs push token so the server can notify you. Turn mention alerts off, sign out, or uninstall and that push token is removed (and it is pruned automatically if it goes stale), so no alert is delivered to this device. Turning alerts off stops delivery, not the server-side watching — to stop that and clear the Mention Vault itself, use the in-app delete (To remove below), which removes it right away, or leave the account idle for the 90-day reap. The separate, user-initiated feedback upload is described below.

Retention — what Limerino deletes, and when. The server deletes the data above on its own, without you asking:

  • Idle accounts — 90 days. If your account has no mention-alert entitlement recorded and has gone idle for 90 idle days — no sign-in and no device check-in in that time — the server deletes your identity row, and with it your Mention Vault entries, your device push token, any synced blocked-user IDs, your followed-channel list, and your notification preferences.
  • Vault ceiling. Your Mention Vault is capped; once it is full, the oldest entries are trimmed away as new ones arrive.

You do not have to wait for either of those: To remove below deletes the same data on demand, and Removing your data covers everything on the device.

What Limerino cannot delete: anything Twitch holds. Limerino is a third-party Twitch client. Every rule above is about data Limerino's server holds. Your Twitch account, the chat messages you send, your follows, and your watch activity are Twitch's records, kept on Twitch's servers under Twitch's own privacy policy and retention rules. Limerino cannot delete data that Twitch holds, and none of the deletions above touch it — use Twitch's own controls for that (see Removing your data).

To remove: open Settings → Mention Vault & data → Your data to delete your Mention Vault entries, or all server account data (mentions, device, and entitlement state, plus your followed-channel list and notification preferences), on demand. Both delete actions remove only the data Limerino's server holds; nothing on the App Store side is changed.

Diagnostics (Settings → Diagnostics)

Settings → Diagnostics can generate a read-only status report to help debug a problem: whether you are signed in, which Twitch scopes you granted, your Twitch user-ID, the active channel, and the embedded player's session state. It contains no tokens, passwords, or other secret values — only on/off flags and identifiers. The report is shown on screen and you can copy it; nothing is uploaded automatically. It only leaves the device if you choose to copy and send it, or if you attach it to a feedback submission via Settings → Report a Bug or Suggest a Feature (see Bug reports & feature suggestions below).

Bug reports & feature suggestions (Settings → Support)

Settings → Report a Bug and Suggest a Feature send your typed text to the developer through the same optional, user-initiated upload: nothing is sent unless you type something and tap Submit. When you do, Limerino sends to its backend (api.limerino.com, hosted on Railway):

  • the description you typed;
  • basic device metadata — the app version and build number, your iOS version, your device model (e.g. iPhone16,2), and your system language — which is always included so a report can be reproduced, even when you turn Include diagnostics off. It carries no Twitch identity on its own; and
  • unless you turn off the Include diagnostics toggle (on by default for a bug report, off by default for a feature suggestion), the same read-only diagnostics report described above — which, when you are signed in, includes your Twitch username, display name, and user-ID, the Twitch scopes you granted, the active channel, and the player's session state. It never includes your messages, tokens, or passwords.

While Include diagnostics is on, View what's sent shows — before you submit — the exact diagnostics text that will travel with the submission. This upload is not tied to mention alerts and needs no sign-in — anyone can send one. A bug report is used only to reproduce and fix the problem, and a feature suggestion only to consider the idea. Leaving Include diagnostics off removes Twitch identity from the submission, but the basic device metadata above still travels with it.

Tapping Submit stores the typed description, basic device metadata, and any diagnostics you chose to include in Limerino's private backend database, along with its processing status, the resulting structured triage decision, and request usage/cost metadata. When a request is kept for follow-up, its typed description, basic device metadata, and any diagnostics you chose to include — including the Twitch identity shown in the diagnostics preview — are also copied into an issue or comment in the developer's private GitHub issue tracker. Obvious spam can be rejected without being copied to GitHub.

Submissions are triaged automatically: OpenAI processes the typed description and basic device metadata to classify the submission and check for likely duplicates before it is filed. Diagnostics are never shared for automated triage — they are never sent to OpenAI and stay in Limerino's private backend.

The backend necessarily receives the connection's IP address. It immediately combines that address with a private random salt and stores only the resulting one-way hash for abuse prevention and rate limiting; the raw IP address is not stored. During triage, that salted hash is also sent to OpenAI as a privacy-preserving safety identifier.

To remove: bug reports and feature suggestions are developer-side issues, not stored on your device; email hello@meipath.com to ask for one you sent to be deleted.

Recent-messages backfill (recent-messages.robotty.de)

When you are signed in and open a channel, Limerino can fetch a short window of recent chat from before you joined, so you have scrollback. This comes from the third-party community service recent-messages.robotty.de. Only the channel name is sent — nothing about you, and no token.

To disable: Settings → toggle off Fetch recent messages on join.

Link previews (i.imgur.com, pbs.twimg.com, cdn.discordapp.com, and similar)

When chat contains a link whose URL is on Limerino's small CDN whitelist (typed in Limerino/Features/Chat/Rendering/LinkPreview.swift), the app fetches a thumbnail directly from that CDN over HTTPS to render an inline preview. No referrer is sent; the redirect chain is hard-disabled.

To disable: Settings → Appearance → toggle off Inline link previews.

Reporting (handled by Twitch)

Limerino lets you report an objectionable chat message or user (long-press a message → Report message, or open a user → Report). Because Twitch hosts and moderates the content on its own platform, the in-app Report action opens Twitch's own report flow for that user in your browser, where you complete the report with Twitch.

  • Limerino does not collect, store, or transmit your reports. Nothing about a report is recorded on the device or sent anywhere by Limerino — there is no Limerino-operated server to send it to.
  • You can also Block the user immediately. Blocking is a local action that takes effect right away and stops that user's messages from showing in the app.

Share extension, widgets & Live Activities (App Group, on-device only)

Limerino ships three companion surfaces that need to hand a channel to the main app: the Share extension (share a Twitch link into Limerino from another app), the home-screen widget, and a Live Activity. iOS runs each of these as a separate process, so they exchange data with the main app through a private App Group container (group.com.themizeguy.limerino):

  • The Share extension writes the channel login you shared into the App Group so the main app can open it on next launch.
  • The widget and Live Activity persist a small channel snapshot (login, display name, live/title/viewers used to render the tile) to the same App Group.

This container is part of the app's own private storage. It is local-only — none of it is uploaded anywhere, and it is removed when you uninstall the app.

Siri & Shortcuts ("Open channel in Limerino")

Limerino offers an Open channel in Limerino App Shortcut. When you invoke it, the channel login you speak or type is donated to the system so Siri / Spotlight / Shortcuts can route it back into the app. This donation stays on your device and is handled by iOS; Limerino does not send it anywhere.

To remove donated shortcuts: delete them in the iOS Shortcuts app, or offload/uninstall Limerino.

Removing your data

Limerino has no first-party account — you sign in with Twitch's own login — so there is no separate "delete account" step. You remove what Limerino stores on-device like this:

  • Clear it in the app deletes the saved copy from the device: Whispers → Clear (your stored DMs) and the Inbox → Clear (saved mentions / highlights).
  • Sign out (Settings → Account → Sign out) asks Twitch to revoke the access token (best effort — it is not retried if that network call fails), removes that account's entry from the device Keychain, clears the video player's Twitch web session, and hides the signed-in data from view. It does not delete that account's saved whispers or Inbox — those rows stay owner-scoped on the device and reappear if you sign back into the same account. Use the in-app Clear actions above, or uninstall, to delete them.
  • Uninstall the app removes Limerino's entire on-device sandbox: every SwiftData store (open channels, settings, whispers, Inbox), the per-channel chat-log files, and the shared App Group container.

iOS Keychain items can survive an uninstall in some configurations, so sign out first if you want to be certain the Twitch token is gone. There is no single in-app "erase everything" button today; the steps above are the complete removal path.

Data the Limerino server holds — the identity row and Mention Vault that signing in creates, plus the device push token, followed-channel list, and notification preferences that using mention alerts adds — is deleted on demand from Settings → Mention Vault & data → Your data, and is also deleted automatically once your account goes idle for 90 days with no mention-alert entitlement recorded (see Mention alerts & Mention Vault above for the exact condition). Signing out revokes our copy of your token and removes this device's push registration; it does not, on its own, delete the identity row or Mention Vault already stored, nor stop the server-side monitoring while that row exists — use the in-app delete to remove it now, or leave the account idle for the 90-day reap.

Data Twitch holds is Twitch's, not ours. Limerino is a third-party Twitch client. Your Twitch account, every chat message you send, your follows, and your watch activity are stored on Twitch's servers under Twitch's own privacy policy — not by Limerino, and Limerino cannot delete them. Signing out of Limerino, or deleting everything Limerino holds, removes nothing from Twitch and does not delete your Twitch account or anything you posted to Twitch. To remove or request data that Twitch holds, use Twitch's own account settings and privacy process at twitch.tv.

What Limerino does not do

  • No analytics SDK, no telemetry, no crash-reporter pinging an outside server.
  • No advertising IDs, no ATT prompt, no tracking domains. The privacy manifest declares this and the assertion is regression-tested.
  • No background uploads of your activity or content from your device. The one background data flow is the mention-alert monitoring described above, which the server runs while your identity row exists — it starts at sign-in and, because signing out does not delete that row, continues until you delete it or the 90-day idle reap removes it (the Mention Vault it fills is deleted on demand, or by that reap — see Mention alerts & Mention Vault above). The only other uploads to a Limerino server are the bug reports and feature suggestions you send yourself from Settings (see Bug reports & feature suggestions above), which happen only when you tap Submit. Reporting objectionable chat opens Twitch's own report flow; Limerino keeps no copy, and nothing about a report leaves the device in the background. No location access. No camera access. No microphone access. No contact access. No HealthKit / HomeKit / Motion / Bluetooth.
  • Limerino never logs your access token, refresh token, or any secret.

How the data leaves the device

Scroll sideways for the full table.

DestinationWhenWhat
irc.chat.twitch.tv (Twitch)After the app validates your signed-in Twitch accountTLS IRC frames for channels you open; chat you send when the validated permissions allow it
api.twitch.tv (Twitch Helix)After the app validates your signed-in Twitch accountDocumented OAuth-authenticated REST calls for identity, search, follows, stream and clip details, chat settings, and badges
id.twitch.tv (Twitch OAuth)During sign-in, token refresh, periodic token validation, and the player-session account checkOAuth handshake and validation; the player session's account-verification check
eventsub.wss.twitch.tv (Twitch)When signed inLive stream / moderation event push
7tv.ioAt app start for global emotes; when a signed-in channel loads for channel emotesPublic 7TV emote-set fetches
api.betterttv.netAt app start for global emotes; when a signed-in channel loads for channel emotesPublic BTTV emote-set fetches and global badge metadata
api.frankerfacez.comAt app start for global emotes; when a signed-in channel loads for channel emotesPublic FFZ emote-set and badge fetches
static-cdn.jtvnw.net (Twitch)When chat renders Twitch emotes / badgesEmote / badge id → image bytes (no token, nothing about you)
d3aqoihi2n8ty8.cloudfront.net (Twitch)When chat renders bits / cheermotesCheermote id → image bytes
cdn.7tv.app (7TV)When chat renders 7TV emotesEmote id → image bytes
events.7tv.io (7TV)Socket opens at app start; channel subscriptions begin after signed-in channel hydrationLive emote-set updates
cdn.betterttv.net (BTTV)When chat renders BTTV emotes or badgesEmote or badge id → image bytes
sockets.betterttv.net (BTTV)Socket opens at app start; channel subscriptions begin after signed-in channel hydrationLive emote updates
cdn.frankerfacez.com (FFZ)When chat renders FFZ emotes / badgesEmote id → image bytes
recent-messages.robotty.deWhen signed in and you open a channel (if backfill enabled)Channel name → recent scrollback from before you joined
itunes.apple.com (Apple)Once per app launchApp Store version lookup for the one-time update notice: the app's public bundle id and your device's region setting. Nothing about you or your account
limerino.com (Limerino sign-in bounce)Only if the legacy web sign-in runs — not part of the current sign-in flowLoads Limerino's OAuth redirect bounce page, which forwards the Twitch login result to the app; your token rides the URL fragment and is not received by the server
api.limerino.com (mention alerts — session)When you sign in (establishes your mention-alerts session; monitoring begins)Your Twitch access token, checked against Twitch to confirm who you are then discarded (never stored); the identity row kept for you (Twitch user-ID, login/display name, mention-alert entitlement state); Mention Vault entries the server records for you (message text, channel, chatter login/display name, timestamp); optional blocked-user ID sync
api.limerino.com (mention alerts — alert delivery)While mention alerts are onThis device's APNs push token, so a matched mention can be delivered here
api.limerino.com (mention alerts — notification settings)When you open or adjust Notification settings, or your followed channels changeYour followed-channel list (names only) and notification preferences (per-channel toggles, cooldowns, quiet hours + time zone, delivery mode)
api.limerino.com (Limerino feedback)When you tap Submit in Settings → Report a Bug or Suggest a FeatureYour typed description; always basic device metadata, even with Include diagnostics off; the diagnostics report unless you turn off Include diagnostics (on by default for a bug, off for a suggestion). Every request is stored in Limerino's private backend; a request kept for follow-up is copied to the developer's private GitHub tracker with the same description, metadata, and any included diagnostics. OpenAI receives the description, basic metadata, and salted safety identifier to triage the request automatically; diagnostics never go to OpenAI. No sign-in required
Whitelisted CDNsWhen you tap or scroll past a previewable linkImage thumbnail fetch
www.twitch.tv, player.twitch.tv (Twitch)The in-app device-approval page during sign-in; the video playerTwitch's own activation / login / player web pages, loaded in a secure web view
www.twitch.tv (your browser)When you tap Report on a message / userOpens the reported user's Twitch page in your default browser so you can report them to Twitch — Limerino sends nothing itself
*.ttvnw.net (Twitch)While the video player is playingTwitch video segments from the player's own CDN
On-device App Group (no network)Share into Limerino · pin a widget / Live ActivityChannel login + channel snapshot, app-extension → app
On-device Siri donation (no network)Use the "Open channel in Limerino" shortcutSpoken/typed channel login, donated to iOS for routing

The two twitch.tv rows above are Twitch's own web pages: when you approve a sign-in in the app or use the video player, Limerino loads www.twitch.tv/activate (which routes through www.twitch.tv/login when you need to sign in there) and player.twitch.tv inside a secure web view (WKWebView). Those pages talk to Twitch's servers — including Twitch's video-delivery CDNs (hosts under ttvnw.net) — the same way twitch.tv does in a browser. Limerino adds no destinations of its own there.

Children's privacy and age rating

Limerino does not knowingly collect any data from anyone, including children under 13. The app is rated 17+ on the App Store because chat is unfiltered, third-party user-generated content and can include mature language and links to the open web.

Changes to this policy

If this policy changes, the new version replaces this one in-app on the next release. The release notes will call out the change.

Contact

Questions, requests, or copies of your data: