Overview
These utility functions help you work with poll messages by identifying poll types and extracting structured data from the raw payload.
Check if Message is a Poll
isPollMessage ( message : MessageResponse ): boolean
Determines if a message is a poll message (either poll definition or vote).
Parameters
Returns
true if the message is a poll (either definition or vote), false otherwise
Example
import { isPollMessage } from "@photon-ai/advanced-imessage-kit" ;
sdk . on ( "message" , ( message ) => {
if ( isPollMessage ( message )) {
console . log ( "Received a poll message!" );
}
});
Check if Message is a Poll Vote
isPollVote ( message : MessageResponse ): boolean
Determines if a message is a poll vote (as opposed to the original poll definition).
Parameters
Returns
true if the message is a poll vote, false otherwise
Example
import { isPollMessage , isPollVote } from "@photon-ai/advanced-imessage-kit" ;
sdk . on ( "message" , ( message ) => {
if ( isPollMessage ( message )) {
if ( isPollVote ( message )) {
console . log ( "Someone voted on a poll" );
} else {
console . log ( "A new poll was created" );
}
}
});
Parse Poll Definition
parsePollDefinition ( message : MessageResponse ): ParsedPoll | null
Extracts the poll definition from a poll message, including title, creator, and all options with their identifiers.
Parameters
The poll message to parse (must be a poll definition, not a vote)
Returns
Parsed poll data, or null if the message is not a poll definition The poll question or title
The handle (phone number or email) of the poll creator
Array of poll options Unique identifier for this option (needed for voting)
The option text displayed to users
Attributed text representation
Handle of who created this option
Whether this option can be edited
Example
import { parsePollDefinition , isPollVote } from "@photon-ai/advanced-imessage-kit" ;
sdk . on ( "message" , ( message ) => {
if ( isPollMessage ( message ) && ! isPollVote ( message )) {
const pollData = parsePollDefinition ( message );
if ( pollData ) {
console . log ( `Poll: ${ pollData . title } ` );
console . log ( `By: ${ pollData . creatorHandle } ` );
console . log ( "Options:" );
pollData . options . forEach (( option , index ) => {
console . log ( ` ${ index + 1 } . ${ option . text } ` );
console . log ( ` ID: ${ option . optionIdentifier } ` );
});
}
}
});
Parse Poll Votes
parsePollVotes ( message : MessageResponse ): ParsedPollVote | null
Extracts vote information from a poll vote message.
Parameters
The vote message to parse (must be a poll vote)
Returns
Parsed vote data, or null if the message is not a poll vote Array of votes in this message The option identifier that was voted for
The handle of the person who voted
Server timestamp of when the vote was cast (if available)
Example
import { parsePollVotes , isPollVote , getOptionTextById } from "@photon-ai/advanced-imessage-kit" ;
sdk . on ( "message" , ( message ) => {
if ( isPollMessage ( message ) && isPollVote ( message )) {
const voteData = parsePollVotes ( message );
if ( voteData ) {
voteData . votes . forEach (( vote ) => {
const optionText = getOptionTextById ( vote . voteOptionIdentifier );
const display = optionText ? `" ${ optionText } "` : vote . voteOptionIdentifier ;
console . log ( ` ${ vote . participantHandle } voted for ${ display } ` );
});
}
}
});
Complete Example: Poll Monitoring
import {
iMessageSDK ,
isPollMessage ,
isPollVote ,
parsePollDefinition ,
parsePollVotes ,
} from "@photon-ai/advanced-imessage-kit" ;
const sdk = new iMessageSDK ({ serverUrl: "http://localhost:3000" });
sdk . on ( "ready" , () => {
console . log ( "Monitoring polls..." );
});
sdk . on ( "message" , ( message ) => {
// Check if this is a poll-related message
if ( ! isPollMessage ( message )) {
return ;
}
if ( isPollVote ( message )) {
// Handle vote messages
const voteData = parsePollVotes ( message );
if ( voteData && voteData . votes . length > 0 ) {
console . log ( " \n [POLL VOTE]" );
voteData . votes . forEach (( vote ) => {
console . log ( ` ${ vote . participantHandle } voted` );
console . log ( ` Option: ${ vote . voteOptionIdentifier } ` );
if ( vote . serverVoteTime ) {
console . log ( ` Time: ${ new Date ( vote . serverVoteTime ). toLocaleString () } ` );
}
});
}
} else {
// Handle poll definition messages
const pollData = parsePollDefinition ( message );
if ( pollData ) {
console . log ( " \n [NEW POLL]" );
console . log ( `Title: ${ pollData . title || "(no title)" } ` );
console . log ( `Creator: ${ pollData . creatorHandle } ` );
console . log ( `Options ( ${ pollData . options . length } ):` );
pollData . options . forEach (( option , index ) => {
console . log ( ` ${ index + 1 } . ${ option . text } ` );
console . log ( ` ID: ${ option . optionIdentifier } ` );
console . log ( ` Can edit: ${ option . canBeEdited } ` );
});
}
}
});
await sdk . connect ();
Helper Constants
import { POLL_BALLOON_BUNDLE_ID } from "@photon-ai/advanced-imessage-kit" ;
console . log ( POLL_BALLOON_BUNDLE_ID );
// "com.apple.messages.MSMessageExtensionBalloonPlugin:0000000000:com.apple.messages.Polls"
The balloon bundle ID used to identify poll messages.
Notes
isPollMessage() returns true for both poll definitions and votes
isPollVote() only returns true for vote messages (checks if associatedMessageType === "4000")
parsePollDefinition() returns null for vote messages - only use it on poll definitions
parsePollVotes() returns null for poll definitions - only use it on vote messages
Poll data is automatically cached when parsed, making subsequent lookups faster
Option identifiers are required for voting and are unique to each poll option
All parsing functions safely handle invalid or malformed poll messages by returning null
cachePoll
Cache a parsed poll for later lookup by option ID.
Method Signature
import { cachePoll , type ParsedPoll } from "@photon-ai/advanced-imessage-kit" ;
cachePoll ( messageGuid : string , poll : ParsedPoll ): void
Parameters
The parsed poll object to cache
Example
import { parsePollDefinition , cachePoll } from "@photon-ai/advanced-imessage-kit" ;
const pollData = parsePollDefinition ( message );
if ( pollData ) {
cachePoll ( message . guid , pollData );
}
Poll definitions are automatically cached when parsed. Manual caching is only needed for custom scenarios.
getCachedPoll
Retrieve a previously cached poll by message GUID.
Method Signature
import { getCachedPoll , type ParsedPoll } from "@photon-ai/advanced-imessage-kit" ;
getCachedPoll ( messageGuid : string ): ParsedPoll | null
Parameters
Returns
Returns the cached ParsedPoll object, or null if not found.
Example
import { getCachedPoll } from "@photon-ai/advanced-imessage-kit" ;
const poll = getCachedPoll ( "poll-message-guid" );
if ( poll ) {
console . log ( `Poll: ${ poll . title } ` );
poll . options . forEach ( opt => {
console . log ( `- ${ opt . text } ` );
});
}
getPollOneLiner
Get a one-line summary of a poll message.
Method Signature
import { getPollOneLiner } from "@photon-ai/advanced-imessage-kit" ;
getPollOneLiner ( message : MessageResponse ): string | null
Parameters
Returns
Returns a one-line string summary, or null if not a poll message.
Example
import { isPollMessage , getPollOneLiner } from "@photon-ai/advanced-imessage-kit" ;
sdk . on ( "new-message" , ( message ) => {
if ( isPollMessage ( message )) {
const summary = getPollOneLiner ( message );
console . log ( summary );
// Output: "Poll: What's for dinner? (3 options)"
}
});
getPollSummary
Get a detailed summary of a poll message including options.
Method Signature
import { getPollSummary } from "@photon-ai/advanced-imessage-kit" ;
getPollSummary ( message : MessageResponse ): string | null
Parameters
Returns
Returns a multi-line formatted summary, or null if not a poll message.
Example
import { isPollMessage , getPollSummary } from "@photon-ai/advanced-imessage-kit" ;
sdk . on ( "new-message" , ( message ) => {
if ( isPollMessage ( message )) {
const summary = getPollSummary ( message );
console . log ( summary );
/* Output:
Poll: What's for dinner?
Created by: [email protected]
Options:
- Pizza
- Sushi
- Tacos
*/
}
});