feat(sdk): 初始化 Android SDK 核心功能模块
- 添加 SDK 配置管理、网络请求客户端和令牌存储功能 - 实现即时通讯 IM 模块,包括消息收发、群组管理和会话功能 - 集成推送服务和应用更新功能模块 - 创建示例应用演示 SDK 使用方法 - 配置项目依赖管理和构建设置
这个提交包含在:
父节点
bfecb15f55
当前提交
491a1ce8d3
@ -24,7 +24,7 @@ export default defineConfig({
|
|||||||
],
|
],
|
||||||
},
|
},
|
||||||
{ text: 'API 速查', link: '/server/api' },
|
{ text: 'API 速查', link: '/server/api' },
|
||||||
{ text: '平台控制台', link: 'https://sentry.xuqinmin.com', target: '_blank' },
|
{ text: '平台控制台', link: 'https://dev.xuqinmin.com', target: '_blank' },
|
||||||
],
|
],
|
||||||
|
|
||||||
sidebar: {
|
sidebar: {
|
||||||
|
|||||||
@ -1,14 +1,16 @@
|
|||||||
# Android SDK 概览
|
# Android SDK 接入指南
|
||||||
|
|
||||||
**版本**:0.1.0 · **最低 Android 版本**:API 24 (Android 7.0) · **语言**:Kotlin
|
**版本**:0.2.x(v0.4.0 将引入 UserSig 鉴权)· **最低 Android 版本**:API 24 (Android 7.0) · **语言**:Kotlin
|
||||||
|
|
||||||
|
> **注意**:v0.4.0 将是 Breaking 版本,`initialize()` 将保持不变,`ImSDK.login()` 将改为 UserSig 鉴权模式。
|
||||||
|
|
||||||
## 功能模块
|
## 功能模块
|
||||||
|
|
||||||
| 模块 | Artifact | 功能 |
|
| 模块 | Artifact | 功能 |
|
||||||
|------|----------|------|
|
|------|----------|------|
|
||||||
| sdk-core | `com.xuqm:sdk-core` | 初始化、网络、鉴权、设备信息 |
|
| sdk-core | `com.xuqm:sdk-core` | 初始化、网络、鉴权(EncryptedSharedPreferences)|
|
||||||
| sdk-im | `com.xuqm:sdk-im` | 单聊、群聊、消息收发 |
|
| sdk-im | `com.xuqm:sdk-im` | 单聊、群聊、消息收发、会话、好友、群组 |
|
||||||
| sdk-push | `com.xuqm:sdk-push` | 设备 Token 注册、离线推送 |
|
| sdk-push | `com.xuqm:sdk-push` | 自动检测厂商、设备 Token 注册 |
|
||||||
| sdk-update | `com.xuqm:sdk-update` | App 更新检查、RN 热更新 |
|
| sdk-update | `com.xuqm:sdk-update` | App 更新检查、RN 热更新 |
|
||||||
|
|
||||||
## 快速接入
|
## 快速接入
|
||||||
@ -28,40 +30,39 @@ dependencyResolutionManagement {
|
|||||||
```kotlin
|
```kotlin
|
||||||
// app/build.gradle.kts
|
// app/build.gradle.kts
|
||||||
dependencies {
|
dependencies {
|
||||||
implementation("com.xuqm:sdk-core:0.1.0")
|
implementation("com.xuqm:sdk-core:0.2.0")
|
||||||
implementation("com.xuqm:sdk-im:0.1.0") // 按需
|
implementation("com.xuqm:sdk-im:0.2.0")
|
||||||
implementation("com.xuqm:sdk-update:0.1.0") // 按需
|
implementation("com.xuqm:sdk-push:0.2.0") // 按需
|
||||||
|
implementation("com.xuqm:sdk-update:0.2.0") // 按需
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
### 2. 初始化
|
### 2. 初始化
|
||||||
|
|
||||||
|
只需传入 `appId`,服务器地址由 SDK 内置,**无需传 `serverUrl`**。
|
||||||
|
|
||||||
```kotlin
|
```kotlin
|
||||||
// Application.onCreate()
|
// Application.onCreate()
|
||||||
XuqmSDK.init(
|
XuqmSDK.initialize(
|
||||||
context = this,
|
context = this,
|
||||||
appKey = "your_app_id",
|
appId = "your_app_id", // 在租户平台创建应用后获得
|
||||||
appSecret = "your_app_secret", // 建议由服务端签发临时凭证
|
logLevel = LogLevel.WARN, // 可选,DEBUG 开启详细日志
|
||||||
apiBaseUrl = "https://sentry.xuqinmin.com",
|
|
||||||
imBaseUrl = "wss://sentry.xuqinmin.com/ws/im",
|
|
||||||
debug = BuildConfig.DEBUG
|
|
||||||
)
|
)
|
||||||
```
|
```
|
||||||
|
|
||||||
### 3. IM 登录与收消息
|
### 3. IM 登录与收消息
|
||||||
|
|
||||||
```kotlin
|
```kotlin
|
||||||
// 先从你的服务端换取 IM Token,再登录
|
// 登录(协程 suspend 函数)
|
||||||
ImSDK.login(
|
lifecycleScope.launch {
|
||||||
appId = "your_app_id",
|
ImSDK.login(userId = "user_001", nickname = "张三")
|
||||||
userId = "user_001",
|
}
|
||||||
nickname = "张三"
|
|
||||||
)
|
|
||||||
|
|
||||||
// 监听事件
|
// 监听实时消息
|
||||||
ImSDK.addListener(object : ImEventListener {
|
ImSDK.addListener(object : ImEventListener {
|
||||||
override fun onConnected() { /* WebSocket 已连接 */ }
|
override fun onConnected() { /* WebSocket 已连接 */ }
|
||||||
override fun onMessage(msg: ImMessage) { /* 处理收到的消息 */ }
|
override fun onMessage(msg: ImMessage) { /* 单聊消息 */ }
|
||||||
|
override fun onGroupMessage(msg: ImMessage) { /* 群聊消息 */ }
|
||||||
override fun onDisconnected(reason: String?) { /* 断线处理 */ }
|
override fun onDisconnected(reason: String?) { /* 断线处理 */ }
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
@ -69,12 +70,49 @@ ImSDK.addListener(object : ImEventListener {
|
|||||||
### 4. 发送消息
|
### 4. 发送消息
|
||||||
|
|
||||||
```kotlin
|
```kotlin
|
||||||
|
// 发送文本(通过 WebSocket 实时发送)
|
||||||
ImSDK.sendMessage(
|
ImSDK.sendMessage(
|
||||||
toId = "user_002",
|
toId = "user_002",
|
||||||
chatType = ChatType.SINGLE,
|
chatType = "SINGLE",
|
||||||
msgType = MsgType.TEXT,
|
msgType = "TEXT",
|
||||||
content = "Hello!"
|
content = """{"text":"Hello!"}""",
|
||||||
)
|
)
|
||||||
```
|
```
|
||||||
|
|
||||||
[→ 完整安装配置](./setup) · [→ IM 接入详解](./im) · [→ API Reference](./api)
|
### 5. 群组、好友、会话
|
||||||
|
|
||||||
|
```kotlin
|
||||||
|
// 群组
|
||||||
|
val groups = ImSDK.listGroups()
|
||||||
|
val group = ImSDK.createGroup("项目讨论", listOf("user_002", "user_003"))
|
||||||
|
ImSDK.addGroupMember(groupId, "user_004")
|
||||||
|
ImSDK.leaveGroup(groupId)
|
||||||
|
|
||||||
|
// 好友
|
||||||
|
val friends = ImSDK.listFriends()
|
||||||
|
ImSDK.addFriend("user_002")
|
||||||
|
|
||||||
|
// 会话
|
||||||
|
val conversations = ImSDK.listConversations()
|
||||||
|
ImSDK.setConversationPinned(targetId, "SINGLE", true)
|
||||||
|
ImSDK.markRead(targetId)
|
||||||
|
```
|
||||||
|
|
||||||
|
### 6. 推送设备注册
|
||||||
|
|
||||||
|
```kotlin
|
||||||
|
// 登录后调用;SDK 自动检测手机厂商(华为/小米/OPPO/vivo/荣耀)
|
||||||
|
PushSDK.registerDevice(context, userId = "user_001")
|
||||||
|
```
|
||||||
|
|
||||||
|
### 7. 版本更新
|
||||||
|
|
||||||
|
```kotlin
|
||||||
|
// 检查 App 更新
|
||||||
|
val update = UpdateSDK.checkAppUpdate(context)
|
||||||
|
if (update?.needsUpdate == true) {
|
||||||
|
UpdateSDK.downloadAndInstall(context, update.downloadUrl)
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
[→ 完整 API Reference](./api)
|
||||||
|
|||||||
@ -4,7 +4,7 @@
|
|||||||
|
|
||||||
## 1. 注册账号与创建应用
|
## 1. 注册账号与创建应用
|
||||||
|
|
||||||
1. 访问 [XuqmGroup 控制台](https://sentry.xuqinmin.com)
|
1. 访问 [XuqmGroup 控制台](https://dev.xuqinmin.com)
|
||||||
2. 注册租户账号,创建应用
|
2. 注册租户账号,创建应用
|
||||||
3. 记录 `appId`(即 `appKey`)
|
3. 记录 `appId`(即 `appKey`)
|
||||||
|
|
||||||
@ -23,8 +23,8 @@
|
|||||||
所有 SDK 均可直接连接演示环境验证功能:
|
所有 SDK 均可直接连接演示环境验证功能:
|
||||||
|
|
||||||
```
|
```
|
||||||
API 地址:https://sentry.xuqinmin.com
|
API 地址:https://dev.xuqinmin.com
|
||||||
WS 地址:wss://sentry.xuqinmin.com/ws/im
|
WS 地址:wss://dev.xuqinmin.com/ws/im
|
||||||
演示 AppId:ak_demo_chat
|
演示 AppId:ak_demo_chat
|
||||||
演示用户:demo_alice / demo_bob
|
演示用户:demo_alice / demo_bob
|
||||||
```
|
```
|
||||||
|
|||||||
@ -47,8 +47,8 @@ export default class EntryAbility extends UIAbility {
|
|||||||
appId: 'your_app_id',
|
appId: 'your_app_id',
|
||||||
appKey: 'your_app_id',
|
appKey: 'your_app_id',
|
||||||
appSecret: 'your_app_secret',
|
appSecret: 'your_app_secret',
|
||||||
apiBaseUrl: 'https://sentry.xuqinmin.com',
|
apiBaseUrl: 'https://dev.xuqinmin.com',
|
||||||
imWsUrl: 'wss://sentry.xuqinmin.com/ws/im',
|
imWsUrl: 'wss://dev.xuqinmin.com/ws/im',
|
||||||
debug: true,
|
debug: true,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|||||||
@ -10,7 +10,7 @@ hero:
|
|||||||
link: /guide/quickstart
|
link: /guide/quickstart
|
||||||
- theme: alt
|
- theme: alt
|
||||||
text: 平台控制台
|
text: 平台控制台
|
||||||
link: https://sentry.xuqinmin.com
|
link: https://dev.xuqinmin.com
|
||||||
|
|
||||||
features:
|
features:
|
||||||
- icon: 🤖
|
- icon: 🤖
|
||||||
|
|||||||
@ -54,8 +54,8 @@ import XuqmCore
|
|||||||
XuqmSDK.shared.initialize(
|
XuqmSDK.shared.initialize(
|
||||||
appKey: "your_app_id",
|
appKey: "your_app_id",
|
||||||
appSecret: "your_app_secret",
|
appSecret: "your_app_secret",
|
||||||
apiBaseUrl: "https://sentry.xuqinmin.com",
|
apiBaseUrl: "https://dev.xuqinmin.com",
|
||||||
imWsUrl: "wss://sentry.xuqinmin.com/ws/im",
|
imWsUrl: "wss://dev.xuqinmin.com/ws/im",
|
||||||
debug: false
|
debug: false
|
||||||
)
|
)
|
||||||
```
|
```
|
||||||
|
|||||||
@ -1,17 +1,23 @@
|
|||||||
# React Native SDK 概览
|
# React Native SDK 接入指南
|
||||||
|
|
||||||
**包名**:`@xuqm/rn-sdk` · **版本**:0.3.0 · **支持**:React Native 0.73+
|
**包名**:`@xuqm/rn-sdk` · **版本**:0.3.x(v0.4.0 规划中,将引入 UserSig 鉴权)
|
||||||
|
|
||||||
|
> **注意**:v0.4.0 将是 Breaking 版本。`initialize()` 将移除 `serverUrl` 参数,`login()` 将改为 UserSig 鉴权模式,详见[迁移指南](#迁移指南-v03x--v04x)。
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
## 功能模块
|
## 功能模块
|
||||||
|
|
||||||
| 包 | 功能 |
|
| 包 | 功能 |
|
||||||
|----|------|
|
|----|------|
|
||||||
| `@xuqm/rn-common` | 初始化、网络、设备信息(必须) |
|
| `@xuqm/rn-common` | 初始化、网络、设备信息(必须) |
|
||||||
| `@xuqm/rn-im` | 单聊、群聊、消息收发、本地 DB |
|
| `@xuqm/rn-im` | 单聊、群聊、消息收发、本地 DB(WatermelonDB)|
|
||||||
| `@xuqm/rn-push` | 推送设备 Token 上报 |
|
| `@xuqm/rn-push` | 推送设备 Token 上报 |
|
||||||
| `@xuqm/rn-update` | App 版本检查、RN Bundle 热更新 |
|
| `@xuqm/rn-update` | App 版本检查、RN Bundle 热更新 |
|
||||||
| `@xuqm/rn-sdk` | 以上所有模块的 meta 包(推荐直接使用) |
|
| `@xuqm/rn-sdk` | 以上所有模块的 meta 包(推荐直接使用) |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
## 安装
|
## 安装
|
||||||
|
|
||||||
在项目根目录创建 `.npmrc`:
|
在项目根目录创建 `.npmrc`:
|
||||||
@ -26,207 +32,249 @@
|
|||||||
yarn add @xuqm/rn-sdk
|
yarn add @xuqm/rn-sdk
|
||||||
```
|
```
|
||||||
|
|
||||||
或按需安装(减小包体积):
|
---
|
||||||
|
|
||||||
```bash
|
## 快速接入(当前 v0.3.x)
|
||||||
yarn add @xuqm/rn-common @xuqm/rn-im
|
|
||||||
```
|
|
||||||
|
|
||||||
## 快速接入
|
### 1. 初始化
|
||||||
|
|
||||||
### 1. 初始化(推荐异步方式)
|
初始化只需传入 `appId`,服务器地址由 SDK 内置,**不需要传 `serverUrl`**。
|
||||||
|
|
||||||
```ts
|
```ts
|
||||||
import { XuqmSDK } from '@xuqm/rn-sdk'
|
import { XuqmSDK } from '@xuqm/rn-sdk'
|
||||||
|
|
||||||
// 推荐:从租户平台拉取完整配置
|
// App 入口(如 App.tsx 的顶层)
|
||||||
await XuqmSDK.initialize({
|
await XuqmSDK.initialize({
|
||||||
appId: 'your_app_id',
|
appId: 'your_app_id', // 在租户平台创建应用后获得
|
||||||
serverUrl: 'https://your-server.com',
|
logLevel: __DEV__ ? 'debug' : 'warn', // 可选
|
||||||
debug: __DEV__,
|
|
||||||
})
|
|
||||||
|
|
||||||
// 兼容:同步初始化,不发网络请求,根据 serverUrl 推导 URL
|
|
||||||
XuqmSDK.init({
|
|
||||||
appId: 'your_app_id',
|
|
||||||
serverUrl: 'https://your-server.com',
|
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
> `initialize` 自动从 `GET /api/sdk/config?appId=` 获取 imWsUrl、fileServiceUrl 等配置,并在网络失败时 fallback 到 serverUrl 推导值。
|
> SDK 内部自动处理服务器地址、WebSocket 连接、文件服务等配置,开发者无需关心。
|
||||||
|
|
||||||
### 2. IM 登录
|
### 2. IM 登录
|
||||||
|
|
||||||
```ts
|
```ts
|
||||||
import { ImSDK } from '@xuqm/rn-sdk'
|
import { ImSDK } from '@xuqm/rn-sdk'
|
||||||
|
|
||||||
// 使用 IM token(由你的业务服务端签发)
|
// 登录(userId + 用户信息)
|
||||||
await ImSDK.loginWithToken('user_001', 'im_token_from_server', 'xuqm_im')
|
// v0.3.x:传入用户信息,本地 DB 按 userId 自动隔离
|
||||||
|
await ImSDK.login('user_001', 'nickname', 'https://avatar.url')
|
||||||
|
|
||||||
// 直接登录(适用于 im-service 直接认证场景)
|
// 推荐提前在您的服务端生成 UserSig(v0.4.0 正式采用)
|
||||||
await ImSDK.login('user_001', '张三', 'https://cdn.example.com/avatar.jpg', 'xuqm_im')
|
// const userSig = await yourApi.getUserSig(userId)
|
||||||
|
// await ImSDK.login('user_001', userSig)
|
||||||
```
|
```
|
||||||
|
|
||||||
### 3. 监听消息与连接状态
|
### 3. 消息收发
|
||||||
|
|
||||||
```ts
|
```ts
|
||||||
import type { ImEventListener } from '@xuqm/rn-sdk'
|
// 监听实时消息
|
||||||
|
ImSDK.addEventListener('message', (msg) => {
|
||||||
const listener: ImEventListener = {
|
console.log('收到消息:', msg.msgType, msg.content)
|
||||||
onConnected() { console.log('WS 已连接') },
|
|
||||||
onDisconnected(reason) { console.log('WS 断开:', reason) },
|
|
||||||
onMessage(msg) { /* 收到单聊消息 */ },
|
|
||||||
onGroupMessage(msg) { /* 收到群聊消息 */ },
|
|
||||||
onError(err) { console.error(err) },
|
|
||||||
}
|
|
||||||
|
|
||||||
ImSDK.addListener(listener)
|
|
||||||
return () => ImSDK.removeListener(listener)
|
|
||||||
```
|
|
||||||
|
|
||||||
### 4. 发送消息
|
|
||||||
|
|
||||||
```ts
|
|
||||||
// 文本消息
|
|
||||||
const msg = await ImSDK.sendMessage('user_002', 'SINGLE', 'TEXT', 'Hello!')
|
|
||||||
|
|
||||||
// 图片(SDK 自动上传到 file-service)
|
|
||||||
const msg = await ImSDK.sendImageMessage('user_002', 'SINGLE', localUri, width, height)
|
|
||||||
|
|
||||||
// 视频
|
|
||||||
const msg = await ImSDK.sendVideoMessage('user_002', 'SINGLE', localUri, thumbnailUri, durationSeconds)
|
|
||||||
|
|
||||||
// 语音
|
|
||||||
const msg = await ImSDK.sendAudioMessage('user_002', 'SINGLE', localUri, durationSeconds)
|
|
||||||
|
|
||||||
// 文件
|
|
||||||
const msg = await ImSDK.sendFileMessage('user_002', 'SINGLE', localUri, 'report.pdf', fileSize)
|
|
||||||
```
|
|
||||||
|
|
||||||
### 5. 拉取历史消息
|
|
||||||
|
|
||||||
```ts
|
|
||||||
// 单聊历史(先读本地 DB,再回源服务端)
|
|
||||||
const history = await ImSDK.fetchHistory('user_002', 0, 30)
|
|
||||||
|
|
||||||
// 群聊历史
|
|
||||||
const gHistory = await ImSDK.fetchGroupHistory(groupId, 0, 30)
|
|
||||||
```
|
|
||||||
|
|
||||||
### 6. 会话列表(响应式)
|
|
||||||
|
|
||||||
```ts
|
|
||||||
// 订阅本地 DB 变更,新消息/已读/静音/置顶都会触发回调
|
|
||||||
const unsub = ImSDK.subscribeConversations((convs) => {
|
|
||||||
setConversations(convs)
|
|
||||||
})
|
})
|
||||||
return unsub // 组件卸载时调用
|
|
||||||
|
// 发送文本消息
|
||||||
|
const msg = await ImSDK.sendMessage(
|
||||||
|
'user_002', // toId
|
||||||
|
'SINGLE', // chatType: 'SINGLE' | 'GROUP'
|
||||||
|
'TEXT', // msgType
|
||||||
|
'Hello!' // content
|
||||||
|
)
|
||||||
|
|
||||||
|
// 发送图片(自动上传到 file-service)
|
||||||
|
const msg = await ImSDK.sendImageMessage(
|
||||||
|
'user_002', 'SINGLE',
|
||||||
|
'/path/to/image.jpg', // 本地 URI
|
||||||
|
800, 600 // 宽高(可选)
|
||||||
|
)
|
||||||
|
|
||||||
|
// 获取历史消息(单聊)
|
||||||
|
const history = await ImSDK.fetchHistory('user_002', page, size)
|
||||||
|
|
||||||
|
// 获取群历史消息
|
||||||
|
const groupHistory = await ImSDK.fetchGroupHistory('group_xxx', page, size)
|
||||||
|
```
|
||||||
|
|
||||||
|
### 4. 会话列表
|
||||||
|
|
||||||
|
```ts
|
||||||
|
// 订阅会话变化
|
||||||
|
const unsub = ImSDK.subscribeConversations((conversations) => {
|
||||||
|
// conversations: ConversationData[]
|
||||||
|
console.log(conversations)
|
||||||
|
})
|
||||||
|
|
||||||
|
// 置顶会话
|
||||||
|
await ImSDK.setConversationPinned('user_002', 'SINGLE', true)
|
||||||
|
|
||||||
|
// 免打扰
|
||||||
|
await ImSDK.setConversationMuted('group_xxx', 'GROUP', true)
|
||||||
|
|
||||||
// 标记已读
|
// 标记已读
|
||||||
await ImSDK.markRead('user_002')
|
await ImSDK.markRead('user_002')
|
||||||
|
|
||||||
// 置顶/静音
|
|
||||||
await ImSDK.setConversationPinned('user_002', 'SINGLE', true)
|
|
||||||
await ImSDK.setConversationMuted('user_002', 'SINGLE', true)
|
|
||||||
```
|
```
|
||||||
|
|
||||||
### 7. 群聊
|
### 5. 群组管理
|
||||||
|
|
||||||
```ts
|
```ts
|
||||||
// 创建群
|
// 创建群组
|
||||||
const group = await ImSDK.createGroup('讨论组', ['user_001', 'user_002'])
|
const group = await ImSDK.createGroup('项目讨论', ['user_002', 'user_003'])
|
||||||
|
|
||||||
// 订阅群消息 WebSocket topic
|
// 群组列表(仅返回当前用户所在的群)
|
||||||
ImSDK.subscribeGroup(group.id)
|
const groups = await ImSDK.listGroups()
|
||||||
|
|
||||||
// 群消息撤回
|
// 添加成员
|
||||||
await ImSDK.revokeMessage(messageId)
|
await ImSDK.addGroupMember('group_xxx', 'user_004')
|
||||||
|
|
||||||
|
// 移除成员(需要管理员权限)
|
||||||
|
await ImSDK.removeGroupMember('group_xxx', 'user_004')
|
||||||
|
|
||||||
|
// 退出群聊
|
||||||
|
await ImSDK.leaveGroup('group_xxx')
|
||||||
```
|
```
|
||||||
|
|
||||||
### 8. 好友管理
|
### 6. 好友关系
|
||||||
|
|
||||||
```ts
|
```ts
|
||||||
await ImSDK.addFriend('user_002')
|
// 好友列表
|
||||||
await ImSDK.removeFriend('user_002')
|
|
||||||
const friends = await ImSDK.listFriends()
|
const friends = await ImSDK.listFriends()
|
||||||
|
|
||||||
|
// 添加好友(双向)
|
||||||
|
await ImSDK.addFriend('user_002')
|
||||||
|
|
||||||
|
// 删除好友(双向)
|
||||||
|
await ImSDK.removeFriend('user_002')
|
||||||
```
|
```
|
||||||
|
|
||||||
### 9. 消息搜索
|
### 7. 消息搜索(本地)
|
||||||
|
|
||||||
```ts
|
```ts
|
||||||
const results = await ImSDK.searchMessages({
|
import { ImSDK } from '@xuqm/rn-sdk'
|
||||||
keyword: '关键字',
|
import type { MessageSearchParams } from '@xuqm/rn-sdk'
|
||||||
msgType: 'TEXT', // 可选,过滤消息类型
|
|
||||||
startTime: '2026-01-01', // 可选,时间范围
|
const params: MessageSearchParams = {
|
||||||
endTime: '2026-12-31',
|
keyword: '会议', // 关键词搜索
|
||||||
})
|
toId: 'user_002', // 限定会话(可选)
|
||||||
|
chatType: 'SINGLE', // 限定类型(可选)
|
||||||
|
msgTypes: ['TEXT'], // 限定消息类型(可选)
|
||||||
|
limit: 20,
|
||||||
|
}
|
||||||
|
const results = await ImSDK.searchMessages(params)
|
||||||
```
|
```
|
||||||
|
|
||||||
### 10. App 版本更新
|
### 8. 推送 SDK
|
||||||
|
|
||||||
|
```ts
|
||||||
|
import { PushSDK } from '@xuqm/rn-sdk'
|
||||||
|
|
||||||
|
// 初始化并注册设备(登录后调用)
|
||||||
|
await PushSDK.initialize({ userId: 'user_001' })
|
||||||
|
```
|
||||||
|
|
||||||
|
### 9. 版本更新 SDK
|
||||||
|
|
||||||
```ts
|
```ts
|
||||||
import { UpdateSDK } from '@xuqm/rn-sdk'
|
import { UpdateSDK } from '@xuqm/rn-sdk'
|
||||||
|
|
||||||
// 自动读取原生版本码,无需传参
|
// 检查 App 原生更新
|
||||||
const info = await UpdateSDK.checkAppUpdate()
|
const appUpdate = await UpdateSDK.checkAppUpdate()
|
||||||
if (info?.needsUpdate) {
|
if (appUpdate?.needsUpdate) {
|
||||||
console.log(info.versionName, info.forceUpdate, info.downloadUrl)
|
console.log('新版本:', appUpdate.versionName)
|
||||||
|
// Linking.openURL(appUpdate.downloadUrl)
|
||||||
|
}
|
||||||
|
|
||||||
|
// 检查 RN Bundle 热更新
|
||||||
|
const rnUpdate = await UpdateSDK.checkRnUpdate('your_module_id')
|
||||||
|
if (rnUpdate?.needsUpdate) {
|
||||||
|
await UpdateSDK.downloadAndApplyBundle(rnUpdate)
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
### 11. RN Bundle 热更新
|
### 10. 断开连接
|
||||||
|
|
||||||
```ts
|
```ts
|
||||||
// 插件在 bundle 加载时自注册(自动读取 plugin.json)
|
ImSDK.disconnect()
|
||||||
import meta from './plugin.json' // { moduleId, version }
|
|
||||||
UpdateSDK.registerPlugin(meta)
|
|
||||||
|
|
||||||
// 检查 → 下载 → 缓存(三步)
|
|
||||||
const checkInfo = await UpdateSDK.checkRnUpdate('home')
|
|
||||||
if (checkInfo.needsUpdate) {
|
|
||||||
const source = await UpdateSDK.downloadRnBundle(checkInfo.downloadUrl)
|
|
||||||
await UpdateSDK.cacheRnBundle('home', checkInfo.latestVersion, checkInfo.md5, source)
|
|
||||||
}
|
|
||||||
```
|
```
|
||||||
|
|
||||||
## 消息类型 content 格式
|
---
|
||||||
|
|
||||||
| MsgType | content |
|
## TypeScript 类型参考
|
||||||
|---------|---------|
|
|
||||||
| `TEXT` | 纯文本字符串 |
|
|
||||||
| `IMAGE` | `{"url":"...","thumbnailUrl":"...","width":800,"height":600}` |
|
|
||||||
| `VIDEO` | `{"url":"...","thumbnailUrl":"...","duration":30,"size":1048576}` |
|
|
||||||
| `AUDIO` | `{"url":"...","duration":12,"size":204800}` |
|
|
||||||
| `FILE` | `{"url":"...","name":"report.pdf","size":512000,"mimeType":"application/pdf"}` |
|
|
||||||
| `LOCATION` | `{"lat":39.9042,"lng":116.4074,"address":"北京市","title":"天安门"}` |
|
|
||||||
| `CUSTOM` | 任意 JSON 字符串 |
|
|
||||||
| `NOTIFY` | `{"title":"系统通知","content":"内容","level":"INFO"}` |
|
|
||||||
| `RICH_TEXT` | `{"html":"<b>加粗</b>内容"}` |
|
|
||||||
|
|
||||||
## TypeScript 类型
|
|
||||||
|
|
||||||
```ts
|
```ts
|
||||||
|
// 消息
|
||||||
interface ImMessage {
|
interface ImMessage {
|
||||||
id: string
|
id: string
|
||||||
appId: string
|
fromId: string
|
||||||
fromUserId: string
|
|
||||||
toId: string
|
toId: string
|
||||||
chatType: 'SINGLE' | 'GROUP'
|
chatType: 'SINGLE' | 'GROUP'
|
||||||
msgType: MsgType
|
msgType: 'TEXT' | 'IMAGE' | 'AUDIO' | 'VIDEO' | 'FILE' |
|
||||||
content: string
|
'LOCATION' | 'NOTIFY' | 'CUSTOM' | 'RICH_TEXT' |
|
||||||
status: 'SENT' | 'DELIVERED' | 'READ' | 'REVOKED'
|
'CALL_AUDIO' | 'CALL_VIDEO' | 'FORWARD' | 'REVOKED'
|
||||||
mentionedUserIds?: string
|
content: string // JSON 字符串,结构按 msgType 不同
|
||||||
createdAt: string // ISO 8601
|
status: 'SENDING' | 'SENT' | 'DELIVERED' | 'READ' | 'FAILED' | 'REVOKED'
|
||||||
|
createdAt: number // Unix 毫秒
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 会话
|
||||||
interface ConversationData {
|
interface ConversationData {
|
||||||
targetId: string
|
targetId: string
|
||||||
chatType: 'SINGLE' | 'GROUP'
|
chatType: 'SINGLE' | 'GROUP'
|
||||||
lastMsgContent: string
|
lastMsgContent: string
|
||||||
lastMsgType: string
|
lastMsgType: string
|
||||||
lastMsgTime: number // Unix ms
|
lastMsgTime: number
|
||||||
unreadCount: number
|
unreadCount: number
|
||||||
isMuted: boolean
|
isMuted: boolean
|
||||||
isPinned: boolean
|
isPinned: boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 群组
|
||||||
|
interface ImGroup {
|
||||||
|
id: string
|
||||||
|
name: string
|
||||||
|
creatorId: string
|
||||||
|
memberIds: string // JSON 数组字符串
|
||||||
|
adminIds: string
|
||||||
|
createdAt: number
|
||||||
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 迁移指南(v0.3.x → v0.4.0)
|
||||||
|
|
||||||
|
v0.4.0 预计改动(**Breaking Changes**):
|
||||||
|
|
||||||
|
```diff
|
||||||
|
// 初始化
|
||||||
|
- await XuqmSDK.initialize({ appId: 'xxx', serverUrl: 'https://...' })
|
||||||
|
+ await XuqmSDK.initialize({ appId: 'xxx' }) // serverUrl 内置,无需传入
|
||||||
|
|
||||||
|
// IM 登录(改为 UserSig 鉴权,密码不再传入 SDK)
|
||||||
|
- await ImSDK.login(userId, nickname, avatar, dbName)
|
||||||
|
+ const userSig = await yourServer.getUserSig(userId) // 您的服务端签发
|
||||||
|
+ await ImSDK.login(userId, userSig, { nickname, avatar })
|
||||||
|
// dbName 自动由 appId + userId 派生,无需传入
|
||||||
|
|
||||||
|
// loginWithToken 废弃
|
||||||
|
- await ImSDK.loginWithToken(userId, token, dbName)
|
||||||
|
+ // 统一使用 login(userId, userSig)
|
||||||
|
```
|
||||||
|
|
||||||
|
UserSig 生成方式见[安全设计文档](../../design/02-security-design.md)。
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 常见问题
|
||||||
|
|
||||||
|
**Q: 如何获取 appId?**
|
||||||
|
在 [租户平台](https://dev.xuqinmin.com) 注册账号后,创建应用即可获得 AppId。
|
||||||
|
|
||||||
|
**Q: 为什么不需要传 serverUrl?**
|
||||||
|
XuqmGroup 是托管平台,服务地址统一管理,与腾讯云 IM 等平台的设计一致,开发者只需关心业务逻辑。
|
||||||
|
|
||||||
|
**Q: UserSig 是什么?(v0.4.0)**
|
||||||
|
UserSig 是您的业务服务端用 AppSecret 为用户签发的安全凭证,有效期可配置。AppSecret 绝不下发到客户端。
|
||||||
|
|
||||||
|
**Q: 本地消息存储在哪里?**
|
||||||
|
使用 WatermelonDB(SQLite),按 `appId + userId` 自动隔离,多账号切换安全。
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
# Server API 参考
|
# Server API 参考
|
||||||
|
|
||||||
**Base URL**:`https://sentry.xuqinmin.com`
|
**Base URL**:`https://dev.xuqinmin.com`
|
||||||
|
|
||||||
所有 API 通过 Nginx 反代,无需区分内部端口。
|
所有 API 通过 Nginx 反代,无需区分内部端口。
|
||||||
|
|
||||||
|
|||||||
@ -38,8 +38,8 @@ app.use(createXuqm({
|
|||||||
appId: 'your_app_id',
|
appId: 'your_app_id',
|
||||||
appKey: 'your_app_id',
|
appKey: 'your_app_id',
|
||||||
appSecret: 'your_app_secret',
|
appSecret: 'your_app_secret',
|
||||||
apiBaseUrl: 'https://sentry.xuqinmin.com',
|
apiBaseUrl: 'https://dev.xuqinmin.com',
|
||||||
imWsUrl: 'wss://sentry.xuqinmin.com/ws/im',
|
imWsUrl: 'wss://dev.xuqinmin.com/ws/im',
|
||||||
debug: import.meta.env.DEV,
|
debug: import.meta.env.DEV,
|
||||||
}))
|
}))
|
||||||
|
|
||||||
|
|||||||
@ -6,8 +6,8 @@
|
|||||||
|
|
||||||
| 系统 | 地址 | 说明 |
|
| 系统 | 地址 | 说明 |
|
||||||
|------|------|------|
|
|------|------|------|
|
||||||
| 租户开放平台 | `https://sentry.xuqinmin.com/` | 主账号注册、登录、应用管理 |
|
| 租户开放平台 | `https://dev.xuqinmin.com/` | 主账号注册、登录、应用管理 |
|
||||||
| 运营管理平台 | `https://sentry.xuqinmin.com/ops/` | 内部运营管理入口 |
|
| 运营管理平台 | `https://dev.xuqinmin.com/ops/` | 内部运营管理入口 |
|
||||||
|
|
||||||
## 初始化管理员账号
|
## 初始化管理员账号
|
||||||
|
|
||||||
@ -20,8 +20,8 @@
|
|||||||
|
|
||||||
| 平台 | API Base |
|
| 平台 | API Base |
|
||||||
|------|----------|
|
|------|----------|
|
||||||
| tenant-platform | `https://sentry.xuqinmin.com/api` |
|
| tenant-platform | `https://dev.xuqinmin.com/api` |
|
||||||
| ops-platform | `https://sentry.xuqinmin.com/api` |
|
| ops-platform | `https://dev.xuqinmin.com/api` |
|
||||||
|
|
||||||
## 主要页面
|
## 主要页面
|
||||||
|
|
||||||
@ -74,5 +74,5 @@
|
|||||||
## 环境变量
|
## 环境变量
|
||||||
|
|
||||||
```env
|
```env
|
||||||
VITE_API_BASE_URL=https://sentry.xuqinmin.com/api
|
VITE_API_BASE_URL=https://dev.xuqinmin.com/api
|
||||||
```
|
```
|
||||||
|
|||||||
@ -1,7 +1,7 @@
|
|||||||
import axios from 'axios'
|
import axios from 'axios'
|
||||||
|
|
||||||
const imClient = axios.create({
|
const imClient = axios.create({
|
||||||
baseURL: 'https://sentry.xuqinmin.com',
|
baseURL: 'https://dev.xuqinmin.com',
|
||||||
timeout: 15000,
|
timeout: 15000,
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|||||||
@ -1,7 +1,7 @@
|
|||||||
import axios from 'axios'
|
import axios from 'axios'
|
||||||
|
|
||||||
const updateClient = axios.create({
|
const updateClient = axios.create({
|
||||||
baseURL: 'https://sentry.xuqinmin.com',
|
baseURL: 'https://dev.xuqinmin.com',
|
||||||
timeout: 30000,
|
timeout: 30000,
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|||||||
正在加载...
在新工单中引用
屏蔽一个用户