[iOS · Contacts · #18] Scanning a preauth invitation QR code accepts it immediately without confirmation #26

Open
opened 2026-11-06 13:03:54 +00:00 by asemeniv · 1 comment
Member

[iOS · Contacts · #18] Scanning a preauth invitation QR code accepts it immediately without confirmation
Build: TestFlight 1.1.0 (96)
Date: November 6, 2026
Result: Reproduced once. The QR flow for #18 is not accepted.

Related: #18

Summary
Scanning a preauth invitation QR code immediately accepts the invitation and opens a 1:1 chat without showing a confirmation step.

The expected flow is to display the invited JID and require an explicit Cancel / Add decision before calling accept_invite.

Environment
Role Device Account
Scanner iPhone 13 Pro Max, iOS 26.7.1, build 96 testman@conversations.im
Inviter iPhone 17 Pro Max, iOS 27.0.1, build 96 testman435@another.im
The source code was reviewed at commit 529d77d218 with bundled backend 6f79790cbcf8b8cadc9bcd58eb321a492c3f9003.

Preconditions
A preauth invitation QR code from testman435 is displayed, and the scanning device is on Add Contact → Scan Code.

The two accounts already had mutual subscription from a previous test run. Therefore, this run verifies the absence of confirmation and the invocation of invitation acceptance after scanning. The behavior for a completely new contact was not established in this run.

Steps to reproduce
Display a preauth invitation QR code on the inviting device.

On the receiving device, open Add Contact → Scan Code.

Scan the QR code.

Observe the result without performing any additional Add or Accept action.

Expected result
After scanning, the application should display the invited JID and request explicit confirmation:

Cancel — closes the flow without accepting the invitation.

Add — explicitly accepts the invitation and then calls accept_invite.

Actual result
After scanning, the application immediately opens a 1:1 chat. According to the tester's observation, no additional confirmation is shown.

Diagnostics confirm that the application called:

2026-11-06T12:55:49.616Z — roster accept_invite
account: testman@conversations.im
A roster change for testman435@another.im was recorded 46 ms later.

Source code observation
The build 96 QR flow is consistent with the observed behavior:

ScanCodeButton passes the scanned result to model.use(code).

If the method returns a chat, onDone(chat) is called immediately.

In AddContactModel.use, the invitation branch directly calls client.acceptInvite(account, code).

There is no confirmation step between recognizing the invitation and accepting it.

Relevant code:

NewChatViews.swift:200

ComposeModels.swift:189–200

Reproducibility
One documented QR test run.

A 2/2 repetition was not performed because reusing a one-time invitation token is not an appropriate way to establish reproducibility without generating a new invitation.

Retest criteria
Scan a new valid invitation using accounts without an existing subscription. A confirmation dialog with the correct JID must be displayed.

After Cancel, diagnostics must contain no accept_invite or subscription commands, and the contact must not be added.

With a new invitation, Add must result in exactly one invitation acceptance and establish the expected subscription.

Scanning an invitation for an existing contact must still require confirmation and must not create duplicate contacts or chats.

External XMPP links should continue to require confirmation before accepting an invitation.

[iOS · Contacts · #18] Scanning a preauth invitation QR code accepts it immediately without confirmation Build: TestFlight 1.1.0 (96) Date: November 6, 2026 Result: Reproduced once. The QR flow for #18 is not accepted. Related: #18 Summary Scanning a preauth invitation QR code immediately accepts the invitation and opens a 1:1 chat without showing a confirmation step. The expected flow is to display the invited JID and require an explicit Cancel / Add decision before calling accept_invite. Environment Role Device Account Scanner iPhone 13 Pro Max, iOS 26.7.1, build 96 testman@conversations.im Inviter iPhone 17 Pro Max, iOS 27.0.1, build 96 testman435@another.im The source code was reviewed at commit 529d77d21891d052eb1b5f7105b8625e1ad2ddad with bundled backend 6f79790cbcf8b8cadc9bcd58eb321a492c3f9003. Preconditions A preauth invitation QR code from testman435 is displayed, and the scanning device is on Add Contact → Scan Code. The two accounts already had mutual subscription from a previous test run. Therefore, this run verifies the absence of confirmation and the invocation of invitation acceptance after scanning. The behavior for a completely new contact was not established in this run. Steps to reproduce Display a preauth invitation QR code on the inviting device. On the receiving device, open Add Contact → Scan Code. Scan the QR code. Observe the result without performing any additional Add or Accept action. Expected result After scanning, the application should display the invited JID and request explicit confirmation: Cancel — closes the flow without accepting the invitation. Add — explicitly accepts the invitation and then calls accept_invite. Actual result After scanning, the application immediately opens a 1:1 chat. According to the tester's observation, no additional confirmation is shown. Diagnostics confirm that the application called: 2026-11-06T12:55:49.616Z — roster accept_invite account: testman@conversations.im A roster change for testman435@another.im was recorded 46 ms later. Source code observation The build 96 QR flow is consistent with the observed behavior: ScanCodeButton passes the scanned result to model.use(code). If the method returns a chat, onDone(chat) is called immediately. In AddContactModel.use, the invitation branch directly calls client.acceptInvite(account, code). There is no confirmation step between recognizing the invitation and accepting it. Relevant code: NewChatViews.swift:200 ComposeModels.swift:189–200 Reproducibility One documented QR test run. A 2/2 repetition was not performed because reusing a one-time invitation token is not an appropriate way to establish reproducibility without generating a new invitation. Retest criteria Scan a new valid invitation using accounts without an existing subscription. A confirmation dialog with the correct JID must be displayed. After Cancel, diagnostics must contain no accept_invite or subscription commands, and the contact must not be added. With a new invitation, Add must result in exactly one invitation acceptance and establish the expected subscription. Scanning an invitation for an existing contact must still require confirmation and must not create duplicate contacts or chats. External XMPP links should continue to require confirmation before accepting an invitation.
Contributor

Fixed in branch fix/app-issues-25-28 (https://dev.another.im/another-im/anotherim-swift/compare/master...fix/app-issues-25-28), commit ed0d2375: a scanned (or pasted) invitation code no longer goes straight to roster accept_invite; Add Contact keeps it and shows the same question as an invitation link from outside (#18), the one view modifier invitationPrompt now used by both. Cancel accepts nothing; Add accepts once and opens the chat (an existing contact's chat, no duplicate). Tests: ComposeCoreTests. To check on a device: the question appears once the scanner sheet has closed.

Fixed in branch `fix/app-issues-25-28` (https://dev.another.im/another-im/anotherim-swift/compare/master...fix/app-issues-25-28), commit ed0d2375: a scanned (or pasted) invitation code no longer goes straight to `roster accept_invite`; Add Contact keeps it and shows the same question as an invitation link from outside (#18), the one view modifier `invitationPrompt` now used by both. Cancel accepts nothing; Add accepts once and opens the chat (an existing contact's chat, no duplicate). Tests: ComposeCoreTests. To check on a device: the question appears once the scanner sheet has closed.
Sign in to join this conversation.
No labels
done
fixed
returned
No milestone
No project
No assignees
2 participants
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set

Reference
another-im/anotherim-swift#26
No description provided.