mob_sms

SMS composer for Mob apps. Opens the user's default messaging app pre-filled with recipient + body; the user taps Send to actually send. No dangerous permissions on either platform. Cross-platform surface (MobSms.compose/2), per-platform delivery asymmetry documented honestly.

Install

Requires mob 0.9.0 or newer.

def deps do
[
{:mob, "~> 0.9.0"},
{:mob_sms, "~> 0.1"}
]
end

In mob.exs, activate the plugin:

config :mob, :plugins, [:mob_sms]

Usage

MobSms.compose(socket,
to: "+15551234567",
body: "Join me on Sample App: https://example.com/i/ABC123"
)

Both :to and :body are optional. Omit :to to let the user pick a recipient from Contacts inside the composer.

Result arrives as a message to the calling process:

def handle_info({:sms, :sent}, socket), do: ... # iOS
def handle_info({:sms, :cancelled}, socket), do: ... # iOS
def handle_info({:sms, :composer_opened}, socket), do: ... # Android
def handle_info({:sms, :not_available}, socket), do: ... # both

Per-platform delivery — the asymmetry to know

This asymmetry is by design at the platform layer, not something the plugin can paper over. Android intentionally hands the user off to a separate app rather than embedding a sheet; iOS presents inline and can observe the outcome.

Common use cases

What this plugin is NOT

Not silent-send. iOS has no public API for sending SMS without the user tapping Send; Apple treats that as a bright-line spam surface. Android can silent-send via SmsManager.sendTextMessage under the SEND_SMS runtime permission, but Google Play rejects that permission request for most non-SMS-centric apps (the "Permissions Declaration" gate).

If you have a real reason to bypass the sheet on Android — and can accept iOS being permanently in composer mode — a separate send/2 on this module can land in a later release. Talk to us before designing around it.

License

MIT.