Skip to content

Add iOS local network permission description - #255

Open
Techdox wants to merge 1 commit into
ghenry22:masterfrom
Techdox:agent/fix-ios-local-network-permission
Open

Add iOS local network permission description#255
Techdox wants to merge 1 commit into
ghenry22:masterfrom
Techdox:agent/fix-ios-local-network-permission

Conversation

@Techdox

@Techdox Techdox commented Jul 28, 2026

Copy link
Copy Markdown

What changed

  • add NSLocalNetworkUsageDescription to the Expo-managed iOS Info.plist configuration

Why

iOS requires this usage description before an app can prompt for permission to connect to LAN hosts. Without it, Substreamer does not appear under Settings > Privacy & Security > Local Network, and direct connections to self-hosted music servers can fail.

Validation

  • confirmed Expo config introspection includes the usage description in the generated iOS Info.plist
  • npx tsc --noEmit
  • npx jest --no-coverage --no-watchman

Declare the required Info.plist usage string so iOS can prompt before Substreamer connects to LAN-hosted music servers.
@Techdox

Techdox commented Jul 28, 2026

Copy link
Copy Markdown
Author

Related to - #243

@ghenry22

Copy link
Copy Markdown
Owner

Yep I have that on my todo list, thanks for the PR

ghenry22 added a commit that referenced this pull request Aug 16, 2026
… servers

Fresh iOS installs could not connect to a self-hosted server on the local
network, and Chromecast discovery found no devices. One cause for both.

expo-dev-launcher injects NSLocalNetworkUsageDescription at prebuild and then
adds an Xcode run-script phase that deletes it again from every non-Debug
build, gated on the value containing the literal "Expo Dev Launcher". Being a
devDependency doesn't keep it out of release builds — EAS installs those and
the plugin is auto-applied. So production shipped with no reason string at all,
while still declaring NSBonjourServices for Cast: the app announced it browses
the local network and was never able to ask for permission. On iOS 14-17 the
system prompted anyway, without an explanation, which is why existing users
kept working and only fresh installs broke; iOS 18+ turns that into a silent
denial of both the server connection and the mDNS browse.

Setting our own description defeats the strip simply by not matching its
literal. That is load-bearing and invisible, so the explanation lives in the
plugin that already documents the phase rather than in app.json, which the
release script JSON.parses and rewrites.

Also declares the two Cast Bonjour types ourselves. No plist delta today —
RNQP already supplied them and the strip preserves them — but it stops the
array being deleted outright when the strip removes _expo._tcp, and states the
app's own capabilities in the app's own manifest instead of inheriting whatever
a dependency injects, which is the failure mode above.

Diagnosis and fix from #255 by Techdox.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants