docs(project): 更新需求与开发进度对比报告并完善Android SDK接口定义

- 添加了完整的XuqmGroup平台需求与开发进度对比报告
- 实现了Android SDK的ImApi接口定义,涵盖群组、好友、黑名单等完整功能
- 定义了IM消息、会话、群组、用户资料等核心数据模型
- 实现了Android SDK的ImSDK核心功能类,包括连接管理和消息处理
这个提交包含在:
XuqmGroup 2026-05-02 12:30:31 +08:00
父节点 2efd5d5fc5
当前提交 897d58a691
共有 4 个文件被更改,包括 230 次插入1 次删除

查看文件

@ -1,9 +1,13 @@
import { getConfig } from '../core/sdk' import { getConfig } from '../core/sdk'
import { http } from '../core/http' import { http } from '../core/http'
import type { import type {
BlacklistCheckResult,
BlacklistEntry,
ChatType, ChatType,
ConversationGroupItem,
ConversationView, ConversationView,
FriendRequest, FriendRequest,
GroupReadReceiptSummary,
HistoryQuery, HistoryQuery,
GroupJoinRequest, GroupJoinRequest,
ImGroup, ImGroup,
@ -129,6 +133,33 @@ export function setConversationMuted(targetId: string, chatType: ChatType, muted
) )
} }
export function setConversationHidden(targetId: string, chatType: ChatType, hidden: boolean): Promise<void> {
return http.put<void>(
`/api/im/conversations/${encodeURIComponent(targetId)}/hidden`,
undefined,
appQuery({ chatType, hidden }),
)
}
export function setConversationGroup(targetId: string, chatType: ChatType, groupName?: string): Promise<void> {
return http.put<void>(
`/api/im/conversations/${encodeURIComponent(targetId)}/group`,
undefined,
appQuery({ chatType, groupName }),
)
}
export function listConversationGroups(): Promise<string[]> {
return http.get<string[]>('/api/im/conversation-groups', appQuery())
}
export function listConversationGroupItems(groupName: string): Promise<ConversationGroupItem[]> {
return http.get<ConversationGroupItem[]>(
`/api/im/conversation-groups/${encodeURIComponent(groupName)}`,
appQuery(),
)
}
export function setDraft(targetId: string, chatType: ChatType, draft: string): Promise<void> { export function setDraft(targetId: string, chatType: ChatType, draft: string): Promise<void> {
return http.put<void>( return http.put<void>(
`/api/im/conversations/${encodeURIComponent(targetId)}/draft`, `/api/im/conversations/${encodeURIComponent(targetId)}/draft`,
@ -165,6 +196,34 @@ export function listFriends(): Promise<string[]> {
return http.get<string[]>('/api/im/friends', appQuery()) return http.get<string[]>('/api/im/friends', appQuery())
} }
export function addFriend(friendId: string): Promise<void> {
return http.post<void>('/api/im/friends', undefined, appQuery({ friendId }))
}
export function removeFriend(friendId: string): Promise<void> {
return http.delete<void>(`/api/im/friends/${encodeURIComponent(friendId)}`, appQuery())
}
export function removeAllFriends(): Promise<void> {
return http.delete<void>('/api/im/friends', appQuery())
}
export function setFriendGroup(friendId: string, groupName?: string): Promise<void> {
return http.put<void>(
`/api/im/friends/${encodeURIComponent(friendId)}/group`,
undefined,
appQuery({ groupName }),
)
}
export function listFriendGroups(): Promise<string[]> {
return http.get<string[]>('/api/im/friends/groups', appQuery())
}
export function listFriendsByGroup(groupName: string): Promise<string[]> {
return http.get<string[]>(`/api/im/friends/groups/${encodeURIComponent(groupName)}`, appQuery())
}
export function listGroups(): Promise<ImGroup[]> { export function listGroups(): Promise<ImGroup[]> {
return http.get<ImGroup[]>('/api/im/groups', appQuery()) return http.get<ImGroup[]>('/api/im/groups', appQuery())
} }
@ -204,6 +263,43 @@ export function searchGroupMembers(groupId: string, keyword: string, size = 20):
return http.get<UserProfile[]>(`/api/im/groups/${encodeURIComponent(groupId)}/members/search`, appQuery({ keyword, size })) return http.get<UserProfile[]>(`/api/im/groups/${encodeURIComponent(groupId)}/members/search`, appQuery({ keyword, size }))
} }
export function transferGroupOwner(groupId: string, newOwnerId: string): Promise<ImGroup> {
return http.post<ImGroup>(
`/api/im/groups/${encodeURIComponent(groupId)}/owner`,
{ newOwnerId },
)
}
export function updateGroupAttributes(groupId: string, attributes: Record<string, unknown>): Promise<ImGroup> {
return http.put<ImGroup>(
`/api/im/groups/${encodeURIComponent(groupId)}/attributes`,
attributes,
)
}
export function removeGroupAttributes(groupId: string, keys: string[]): Promise<ImGroup> {
return http.post<ImGroup>(
`/api/im/groups/${encodeURIComponent(groupId)}/attributes/delete`,
{ keys },
)
}
export function listBlacklist(): Promise<BlacklistEntry[]> {
return http.get<BlacklistEntry[]>('/api/im/blacklist', appQuery())
}
export function addToBlacklist(blockedUserId: string): Promise<BlacklistEntry> {
return http.post<BlacklistEntry>('/api/im/blacklist', undefined, appQuery({ blockedUserId }))
}
export function removeFromBlacklist(blockedUserId: string): Promise<void> {
return http.delete<void>('/api/im/blacklist', appQuery({ blockedUserId }))
}
export function checkBlacklist(targetUserId: string): Promise<BlacklistCheckResult> {
return http.get<BlacklistCheckResult>('/api/im/blacklist/check', appQuery({ targetUserId }))
}
export function sendFriendRequest(toUserId: string, remark?: string): Promise<FriendRequest> { export function sendFriendRequest(toUserId: string, remark?: string): Promise<FriendRequest> {
return http.post<FriendRequest>( return http.post<FriendRequest>(
'/api/im/friend-requests', '/api/im/friend-requests',
@ -256,3 +352,11 @@ export function rejectGroupJoinRequest(groupId: string, requestId: string): Prom
appQuery(), appQuery(),
) )
} }
export function adminGroupReadReceipts(groupId: string, messageIds: string[]): Promise<GroupReadReceiptSummary[]> {
return http.post<GroupReadReceiptSummary[]>(
`/api/im/admin/groups/${encodeURIComponent(groupId)}/read-receipts`,
{ messageIds },
appQuery(),
)
}

查看文件

@ -1,6 +1,7 @@
import { ref, shallowRef, onUnmounted, reactive, type Ref } from 'vue' import { ref, shallowRef, onUnmounted, reactive, type Ref } from 'vue'
import { ImClient } from './ImClient' import { ImClient } from './ImClient'
import { import {
addFriend,
deleteConversation, deleteConversation,
acceptFriendRequest, acceptFriendRequest,
acceptGroupJoinRequest, acceptGroupJoinRequest,
@ -11,21 +12,31 @@ import {
locateGroupHistoryPage, locateGroupHistoryPage,
locateHistoryPage, locateHistoryPage,
revokeMessage, revokeMessage,
listConversationGroupItems,
listConversationGroups,
listFriendGroups,
listFriendRequests, listFriendRequests,
listFriends, listFriends,
listFriendsByGroup,
listGroupJoinRequests, listGroupJoinRequests,
listGroups, listGroups,
listConversations, listConversations,
markRead, markRead,
removeAllFriends,
removeFriend,
rejectFriendRequest, rejectFriendRequest,
rejectGroupJoinRequest, rejectGroupJoinRequest,
sendFriendRequest, sendFriendRequest,
sendGroupJoinRequest, sendGroupJoinRequest,
setConversationGroup,
setConversationHidden,
setConversationMuted, setConversationMuted,
setConversationPinned, setConversationPinned,
setFriendGroup,
setDraft, setDraft,
} from './api' } from './api'
import type { import type {
ConversationGroupItem,
ConversationView, ConversationView,
HistoryQuery, HistoryQuery,
ImGroup, ImGroup,
@ -55,9 +66,19 @@ export interface UseImReturn {
setConversationRead: (targetId: string, chatType?: ChatType) => Promise<void> setConversationRead: (targetId: string, chatType?: ChatType) => Promise<void>
setConversationPinnedState: (targetId: string, chatType: ChatType, pinned: boolean) => Promise<void> setConversationPinnedState: (targetId: string, chatType: ChatType, pinned: boolean) => Promise<void>
setConversationMutedState: (targetId: string, chatType: ChatType, muted: boolean) => Promise<void> setConversationMutedState: (targetId: string, chatType: ChatType, muted: boolean) => Promise<void>
setConversationHiddenState: (targetId: string, chatType: ChatType, hidden: boolean) => Promise<void>
setConversationGroupName: (targetId: string, chatType: ChatType, groupName?: string) => Promise<void>
getConversationGroups: () => Promise<string[]>
getConversationGroupItems: (groupName: string) => Promise<ConversationGroupItem[]>
setConversationDraft: (targetId: string, chatType: ChatType, draft: string) => Promise<void> setConversationDraft: (targetId: string, chatType: ChatType, draft: string) => Promise<void>
removeConversation: (targetId: string, chatType: ChatType) => Promise<void> removeConversation: (targetId: string, chatType: ChatType) => Promise<void>
getFriends: () => Promise<string[]> getFriends: () => Promise<string[]>
addFriendById: (friendId: string) => Promise<void>
removeFriendById: (friendId: string) => Promise<void>
clearFriends: () => Promise<void>
setFriendGroupName: (friendId: string, groupName?: string) => Promise<void>
getFriendGroups: () => Promise<string[]>
getFriendsByGroup: (groupName: string) => Promise<string[]>
getGroups: () => Promise<ImGroup[]> getGroups: () => Promise<ImGroup[]>
getGroup: (groupId: string) => Promise<ImGroup> getGroup: (groupId: string) => Promise<ImGroup>
sendFriend: (toUserId: string, remark?: string) => Promise<FriendRequest> sendFriend: (toUserId: string, remark?: string) => Promise<FriendRequest>
@ -202,6 +223,22 @@ export function useIm(): UseImReturn {
return setConversationMuted(targetId, chatType, muted) return setConversationMuted(targetId, chatType, muted)
} }
function setConversationHiddenState(targetId: string, chatType: ChatType, hidden: boolean) {
return setConversationHidden(targetId, chatType, hidden)
}
function setConversationGroupName(targetId: string, chatType: ChatType, groupName?: string) {
return setConversationGroup(targetId, chatType, groupName)
}
function getConversationGroups() {
return listConversationGroups()
}
function getConversationGroupItems(groupName: string) {
return listConversationGroupItems(groupName)
}
function setConversationDraft(targetId: string, chatType: ChatType, draft: string) { function setConversationDraft(targetId: string, chatType: ChatType, draft: string) {
return setDraft(targetId, chatType, draft) return setDraft(targetId, chatType, draft)
} }
@ -214,6 +251,30 @@ export function useIm(): UseImReturn {
return listFriends() return listFriends()
} }
function addFriendById(friendId: string) {
return addFriend(friendId)
}
function removeFriendById(friendId: string) {
return removeFriend(friendId)
}
function clearFriends() {
return removeAllFriends()
}
function setFriendGroupName(friendId: string, groupName?: string) {
return setFriendGroup(friendId, groupName)
}
function getFriendGroups() {
return listFriendGroups()
}
function getFriendsByGroup(groupName: string) {
return listFriendsByGroup(groupName)
}
function getGroups() { function getGroups() {
return listGroups() return listGroups()
} }
@ -274,9 +335,19 @@ export function useIm(): UseImReturn {
setConversationRead, setConversationRead,
setConversationPinnedState, setConversationPinnedState,
setConversationMutedState, setConversationMutedState,
setConversationHiddenState,
setConversationGroupName,
getConversationGroups,
getConversationGroupItems,
setConversationDraft, setConversationDraft,
removeConversation, removeConversation,
getFriends, getFriends,
addFriendById,
removeFriendById,
clearFriends,
setFriendGroupName,
getFriendGroups,
getFriendsByGroup,
getGroups, getGroups,
getGroup, getGroup,
sendFriend, sendFriend,
@ -287,5 +358,5 @@ export function useIm(): UseImReturn {
loadGroupJoinRequests, loadGroupJoinRequests,
approveGroupJoinRequest, approveGroupJoinRequest,
declineGroupJoinRequest, declineGroupJoinRequest,
}) as UseImReturn }) as unknown as UseImReturn
} }

查看文件

@ -4,6 +4,10 @@ export { ImClient } from './im/ImClient'
export { export {
acceptFriendRequest, acceptFriendRequest,
acceptGroupJoinRequest, acceptGroupJoinRequest,
addFriend,
addToBlacklist,
adminGroupReadReceipts,
checkBlacklist,
createGroup, createGroup,
deleteConversation, deleteConversation,
getGroupInfo, getGroupInfo,
@ -13,8 +17,13 @@ export {
locateGroupHistoryPage, locateGroupHistoryPage,
locateHistoryPage, locateHistoryPage,
revokeMessage, revokeMessage,
listBlacklist,
listConversationGroupItems,
listConversationGroups,
listFriendGroups,
listFriendRequests, listFriendRequests,
listFriends, listFriends,
listFriendsByGroup,
listGroupJoinRequests, listGroupJoinRequests,
listGroups, listGroups,
listConversations, listConversations,
@ -25,12 +34,21 @@ export {
searchUsers, searchUsers,
rejectFriendRequest, rejectFriendRequest,
rejectGroupJoinRequest, rejectGroupJoinRequest,
removeAllFriends,
removeFriend,
removeFromBlacklist,
removeGroupAttributes,
sendFriendRequest, sendFriendRequest,
sendGroupJoinRequest, sendGroupJoinRequest,
sendMessage, sendMessage,
setConversationGroup,
setConversationHidden,
setConversationMuted, setConversationMuted,
setConversationPinned, setConversationPinned,
setFriendGroup,
setDraft, setDraft,
transferGroupOwner,
updateGroupAttributes,
updateProfile, updateProfile,
} from './im/api' } from './im/api'
export { useIm } from './im/useIm' export { useIm } from './im/useIm'
@ -40,7 +58,11 @@ export type {
ChatType, ChatType,
MsgStatus, MsgStatus,
ImMessage, ImMessage,
BlacklistCheckResult,
BlacklistEntry,
ConversationGroupItem,
ConversationView, ConversationView,
GroupReadReceiptSummary,
HistoryQuery, HistoryQuery,
ImGroup, ImGroup,
FriendRequest, FriendRequest,

查看文件

@ -47,6 +47,7 @@ export interface ImMessage {
export interface ConversationView { export interface ConversationView {
targetId: string targetId: string
chatType: ChatType chatType: ChatType
conversationGroup?: string | null
lastMsgContent?: string | null lastMsgContent?: string | null
lastMsgType?: string | null lastMsgType?: string | null
lastMsgTime: number lastMsgTime: number
@ -96,9 +97,17 @@ export interface ImGroup {
memberIds: string memberIds: string
adminIds: string adminIds: string
announcement?: string | null announcement?: string | null
memberInfo?: string | null
extAttributes?: string | null
createdAt?: string | number | null createdAt?: string | number | null
} }
export interface ConversationGroupItem {
targetId: string
chatType: ChatType
groupName: string
}
export interface FriendRequest { export interface FriendRequest {
id: string id: string
appId?: string appId?: string
@ -121,6 +130,29 @@ export interface GroupJoinRequest {
reviewedAt?: string | number | null reviewedAt?: string | number | null
} }
export interface BlacklistEntry {
id: string
appId: string
userId: string
blockedUserId: string
createdAt: string | number
}
export interface BlacklistCheckResult {
targetUserId: string
blockedByMe: boolean
blockedByTarget: boolean
eitherBlocked: boolean
}
export interface GroupReadReceiptSummary {
messageId: string
groupId: string
memberCount: number
readCount: number
unreadCount: number
}
export interface SendMessageParams { export interface SendMessageParams {
messageId?: string messageId?: string
toId: string toId: string