Listen for open channel events
The open channel feature uses a single unified OpenChannelHandler interface for all event types: channel operation status (join, leave, destroy), multi-device sync, member mute/ban notifications, metadata changes, and member change events.
Register and remove the handler
Use NCEngine.addOpenChannelHandler() to register an OpenChannelHandler and NCEngine.removeOpenChannelHandler() to remove it.
- Kotlin
- Java
kotlin
NCEngine.addOpenChannelHandler("OPEN_CHANNEL_HANDLER", object : OpenChannelHandler {
// ---- Channel operation events ----
override fun onEntering(event: OpenChannelEnteringEvent) {
// Current user is joining channel: event.channelId
}
override fun onEntered(event: OpenChannelEnteredEvent) {
// Current user successfully joined
// event.channelId, event.response (OpenChannelEnterResponseInfo, may be null)
}
override fun onEnterFailed(event: OpenChannelEnterFailedEvent) {
// Join failed: event.channelId, event.error
}
override fun onExited(event: OpenChannelExitedEvent) {
// Current user left: event.channelId
}
override fun onReset(event: OpenChannelResetEvent) {
// Channel reset (followed by onEntered): event.channelId
}
override fun onChannelDestroyed(event: OpenChannelDestroyedEvent) {
// Channel destroyed: event.channelId, event.type (OpenChannelDestroyType)
}
// ---- Event notifications ----
override fun onNotifyMultiLoginSync(event: OpenChannelNotifyMultiLoginSyncEvent) {
// Multi-device join/leave sync
// event.info.channelId, event.info.status, event.info.reason, event.info.time, event.info.extra
}
override fun onMemberBanned(event: OpenChannelMemberBannedEvent) {
// Member banned or unbanned: event.info (OpenChannelMemberBannedInfo)
}
override fun onMemberMuted(event: OpenChannelMemberMutedEvent) {
// Member muted or unmuted: event.info (OpenChannelMemberMutedInfo)
}
// ---- Metadata events ----
override fun onMetadataSynced(event: OpenChannelMetadataSyncedEvent) {
// KV sync complete after joining: event.channelId
}
override fun onMetadataChanged(event: OpenChannelMetadataChangedEvent) {
// KV entries updated or deleted
for (change in event.changeInfo) {
if (change.isDelete) {
// Key deleted: change.key
} else {
// Key updated: change.key = change.value
}
}
}
// ---- Member change events ----
override fun onMemberChanged(event: OpenChannelMemberChangedEvent) {
val channelId = event.info.channelId
val memberCount = event.info.memberCount
for (action in event.info.actions) {
// action.userId, action.action (OpenChannelMemberActionType)
}
}
})
// Remove the handler
NCEngine.removeOpenChannelHandler("OPEN_CHANNEL_HANDLER")
Java
NCEngine.addOpenChannelHandler("OPEN_CHANNEL_HANDLER", new OpenChannelHandler() {
// ---- Channel operation events ----
@Override
public void onEntering(@NonNull OpenChannelEnteringEvent event) {
// Current user is joining: event.getChannelId()
}
@Override
public void onEntered(@NonNull OpenChannelEnteredEvent event) {
// Current user successfully joined
// event.getChannelId(), event.getResponse() (may be null)
}
@Override
public void onEnterFailed(@NonNull OpenChannelEnterFailedEvent event) {
// Join failed: event.getChannelId(), event.getError()
}
@Override
public void onExited(@NonNull OpenChannelExitedEvent event) {
// Current user left: event.getChannelId()
}
@Override
public void onReset(@NonNull OpenChannelResetEvent event) {
// Channel reset: event.getChannelId()
}
@Override
public void onChannelDestroyed(@NonNull OpenChannelDestroyedEvent event) {
// Channel destroyed: event.getChannelId(), event.getType()
}
// ---- Event notifications ----
@Override
public void onNotifyMultiLoginSync(@NonNull OpenChannelNotifyMultiLoginSyncEvent event) {
// Multi-device sync: event.getInfo().getChannelId(), event.getInfo().getStatus(), event.getInfo().getReason()
}
@Override
public void onMemberBanned(@NonNull OpenChannelMemberBannedEvent event) {
// Ban/unban: event.getInfo()
}
@Override
public void onMemberMuted(@NonNull OpenChannelMemberMutedEvent event) {
// Mute/unmute: event.getInfo()
}
// ---- Metadata events ----
@Override
public void onMetadataSynced(@NonNull OpenChannelMetadataSyncedEvent event) {
// KV sync complete: event.getChannelId()
}
@Override
public void onMetadataChanged(@NonNull OpenChannelMetadataChangedEvent event) {
for (OpenChannelMetadataChangeInfo change : event.getChangeInfo()) {
if (change.isDelete()) {
// Key deleted: change.getKey()
} else {
// Key updated: change.getKey() = change.getValue()
}
}
}
// ---- Member change events ----
@Override
public void onMemberChanged(@NonNull OpenChannelMemberChangedEvent event) {
String channelId = event.getInfo().getChannelId();
int memberCount = event.getInfo().getMemberCount();
List<OpenChannelMemberActionInfo> actions = event.getInfo().getActions();
}
});
// Remove the handler
NCEngine.removeOpenChannelHandler("OPEN_CHANNEL_HANDLER");
OpenChannelEnterResponseInfo properties
When onEntered fires, event.response provides the initial channel state (may be null for legacy callbacks):
| Property | Type | Description |
|---|---|---|
memberCount | Int | Current participant count |
createTime | Long | Channel creation timestamp (ms) |
joinTime | Long | Time the current user joined (ms) |
isAllBanned | Boolean | Whether global mute is enabled for the channel |
isCurrentUserBanned | Boolean | Whether the current user is globally muted |
isCurrentChannelBanned | Boolean | Whether the current user is muted in this channel |
isCurrentChannelInWhitelist | Boolean | Whether the current user is on the mute whitelist |
Callback reference
Channel operation events
| Callback | Event type | Trigger |
|---|---|---|
onEntering | OpenChannelEnteringEvent | Joining is in progress. event.channelId. |
onEntered | OpenChannelEnteredEvent | Successfully joined. event.response contains initial channel state. |
onEnterFailed | OpenChannelEnterFailedEvent | Join failed. event.error contains the reason. |
onExited | OpenChannelExitedEvent | Left voluntarily or kicked. event.channelId. |
onReset | OpenChannelResetEvent | Channel reset; onEntered follows immediately. |
onChannelDestroyed | OpenChannelDestroyedEvent | Only fires if the user was online. event.type: MANUAL (Server API) or AUTO (inactive). |
Event notifications
| Callback | Event type | Trigger |
|---|---|---|
onNotifyMultiLoginSync | OpenChannelNotifyMultiLoginSyncEvent | Current user joined or left on another device. event.info.status: ENTER/EXIT. event.info.reason: exit reason when EXIT. |
onMemberBanned | OpenChannelMemberBannedEvent | Member banned or unbanned (when needNotify: true in Server API). event.info for details. |
onMemberMuted | OpenChannelMemberMutedEvent | Member muted or unmuted (when needNotify: true in Server API). event.info for details. |
OpenChannelMemberMutedInfo properties
| Property | Type | Description |
|---|---|---|
channelId | String | Channel ID |
muteType | OpenChannelMemberMuteType | MUTE or UNMUTE |
durationTime | Long | Mute duration in seconds. -1 means permanent. |
operateTime | Long | Operation timestamp (ms) |
userIdList | List<String> | Affected user IDs |
Metadata events
| Callback | Event type | Trigger |
|---|---|---|
onMetadataSynced | OpenChannelMetadataSyncedEvent | Triggered once on join. event.channelId. |
onMetadataChanged | OpenChannelMetadataChangedEvent | KV entries set, updated, or deleted. Iterate event.changeInfo. Each item: channelId, key, value (null when deleted), isDelete. |
Member change events
| Callback | Event type | Trigger |
|---|---|---|
onMemberChanged | OpenChannelMemberChangedEvent | Members joined or left. event.info contains channelId, memberCount, and actions. Requires Member change monitoring enabled in the Console. |
Multi-device login sync
When the same user is logged in on multiple devices, onNotifyMultiLoginSync fires on other devices when joining or leaving.
OpenChannelNotifyMultiLoginSyncEvent contains an info property with the following fields:
| Property | Type | Description |
|---|---|---|
channelId | String | Open channel ID |
status | OpenChannelSyncStatus | EXIT(0): left. ENTER(1): joined. |
reason | OpenChannelExitReason? | Exit reason when status == EXIT: EXIT_VOLUNTARILY(1) or KICKED_OUT_BY_OTHER_DEVICE(2). |
time | Long | Timestamp (ms) |
extra | String? | Additional info |