Skip to content

Channel import shows generic 'Invalid channel link / key' when private-channel slots are full #61

Description

@MrSurly

Summary

ChannelRepository.importChannel() (used by the "Add channel via link/QR code" dialog) silently returns null when the per-companion private-channel index pool is exhausted, instead of surfacing a specific error. The UI then shows the generic "Invalid channel link / key" snackbar, which is misleading -- the link/key is valid, there's just no free channel slot.

This is not platform-specific. It reproduces on any platform once a companion already has _maxPrivateChannels (currently 7) private channels registered.

Where

lib/repositories/channel_repository.dart, importChannel():

  • Computes nextIndex via _nextIndexFor(localOnly, companionKey) (line ~313).
  • If no index is available, _nextIndexFor returns null, and importChannel just does if (nextIndex == null) return null; -- no exception, no distinguishing error.
  • Contrast with createChannel() / createPrivateChannel() in the same file, which handle the identical "no free index" case by throwing a specific StateError('Maximum number of channels ($_maxPrivateChannels) reached').
  • importChannel()'s blanket try { ... } catch (_) { return null; } also swallows firmware-registration failures (_registerChannelWithFirmware returning !isSuccess) the same way, whereas the create-channel paths surface result.errorCode (including a specific message for error code 3 / max channels).

Repro

  1. Have a companion with 7 private (non-public) channels already registered (indices 1-7 all used).
  2. Try to import an 8th channel via a meshcore://channel/add?name=...&secret=... link, either by pasting the full URL or scanning a QR code, in the "Add channel via link/QR code" dialog.
  3. Observe: "Invalid channel link / key" snackbar, even though the link/secret are well-formed and decode correctly.

Expected

importChannel() should distinguish failure modes the same way createChannel/createPrivateChannel already do, and the UI should show a specific message like "Maximum number of channels reached" instead of the generic invalid-link message.

Suggested fix

Either:

  • Have importChannel() throw the same StateErrors that createChannel/createPrivateChannel throw for max-channels-reached and firmware-registration failure, and let the dialog's existing catch (e) block (around lib/screens/channels_screen.dart) display e.toString(), or
  • Change importChannel()'s return type to something that can carry a specific failure reason instead of ChannelData?.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions