@mica/sdk (SDK contract v1)
    Preparing search index...

    Function useDirectMessages

    • Private, one-to-one messages between two accounts in your app. MICA-390.

      Built on the shared identity layer useAccounts reads: every member names the account you are acting as (account_id, one of useAccounts().getMyAccounts(appId)) and the one at the other end (peer_account_id). Both live in appId, and every call carries it, so a thread is always within one app.

      const dms = useDirectMessages('dating');
      const inbox = await dms.threads(); // every correspondent, across all of my accounts here
      const { rows } = await dms.thread({ account_id: me, peer_account_id: them }); // newest first
      await dms.send({ account_id: me, peer_account_id: them, body: 'hi' });
      await dms.markRead({ account_id: me, peer_account_id: them });

      Reads never reject: threads() answers [] and thread() an empty page on any failure, as every list read in the SDK does. Writes do: send and markRead reject, with a ServiceRefusal when the server keyed its answer, so a caller can tell that nothing happened.

      The server, per app. Owning account_id, the peer being an active account in the same app, no messaging yourself and a block in either direction are checked for every app; whatever else your app needs — "only after a match" — is a policy your app's server half registers. An app with no policy is refused outright, so this hook does nothing until one exists.

      Only its own app's messages. In a sandboxed frame the shell replaces appId with the frame's own before anything is sent, so naming another app still reads and writes your own. Needs the social permission, the same one useAccounts does.

      Parameters

      • appId: string

      Returns {
          markRead: (
              input: { account_id: number; peer_account_id: number },
          ) => Promise<boolean>;
          send: (
              input: { account_id: number; body: string; peer_account_id: number },
          ) => Promise<DirectMessage>;
          thread: (
              query: {
                  account_id: number;
                  cursor?: number | null;
                  limit?: number;
                  peer_account_id: number;
              },
          ) => Promise<{ nextCursor: number | null; rows: DirectMessage[] }>;
          threads: () => Promise<DirectMessageThread[]>;
      }

      • markRead: (input: { account_id: number; peer_account_id: number }) => Promise<boolean>

        Mark everything peer_account_id sent account_id read. Rejects on a refusal.

      • send: (
            input: { account_id: number; body: string; peer_account_id: number },
        ) => Promise<DirectMessage>

        Rejects on a refusal, so a caller can tell nothing was sent.

      • thread: (
            query: {
                account_id: number;
                cursor?: number | null;
                limit?: number;
                peer_account_id: number;
            },
        ) => Promise<{ nextCursor: number | null; rows: DirectMessage[] }>

        One thread, newest first, keyset-paged on the message id. An empty page on failure.

      • threads: () => Promise<DirectMessageThread[]>

        Every correspondent across the player's accounts in this app. [] on failure.