新增:发送消息

This commit is contained in:
安浩浩 2024-05-08 23:09:33 +08:00
parent 93ba6c579a
commit ac66084650
5 changed files with 172 additions and 124 deletions

View File

@ -0,0 +1,42 @@
import request from '@/config/axios'
export interface ImMessageSendReqVO {
clientMessageId: string // 客户端消息编号
receiverId: number // 接收人编号
conversationType: number // 会话类型
contentType: number // 内容类型
content: string // 内容
}
export interface ImMessageSendRespVO {
id: number // 编号
sendTime: string // 发送时间
}
export interface ImMessageRespVO {
id: number // 编号
conversationType: number // 会话类型
senderId: number // 发送人编号
senderNickname: string // 发送人昵称
senderAvatar: string // 发送人头像
receiverId: number // 接收人编号
contentType: number // 内容类型
content: string // 内容
sendTime: string // 发送时间
sequence: number // 序号
}
// 发送消息
export const sendMessage = async (data: ImMessageSendReqVO) => {
return await request.post({ url: `/im/message/send`, data })
}
// 消息列表-拉取大于 sequence 的消息列表
export const pullMessageList = async (params: { sequence: number; size: number }) => {
return await request.get({ url: `/im/message/pull`, params })
}
// 消息列表-根据接收人和发送时间进行分页查询
export const getMessageList = async (params: any) => {
return await request.get({ url: `/im/message/list`, params })
}

View File

@ -1,43 +1,80 @@
const SESSION_MESSAGE_TYPE = {
img: '[图片]',
file: '[文件]',
audio: '[语音]',
loc: '[位置]'
img: '[图片]',
file: '[文件]',
audio: '[语音]',
loc: '[位置]'
}
const CUSTOM_TYPE = {
userCard: '个人名片'
userCard: '个人名片'
}
// const ALL_MESSAGE_TYPE = {
// TEXT: 'txt',
// IMAGE: 'img',
// AUDIO: 'audio',
// LOCAL: 'loc',
// VIDEO: 'video',
// FILE: 'file',
// CUSTOM: 'custom',
// CMD: 'cmd',
// INFORM: 'inform' //这个类型不在环信消息类型内,属于自己定义的一种系统通知类的消息。
// }
const ALL_MESSAGE_TYPE = {
TEXT: 'txt',
IMAGE: 'img',
AUDIO: 'audio',
LOCAL: 'loc',
VIDEO: 'video',
FILE: 'file',
CUSTOM: 'custom',
CMD: 'cmd',
INFORM: 'inform' //这个类型不在环信消息类型内,属于自己定义的一种系统通知类的消息。
TEXT: 101,
IMAGE: 102,
AUDIO: 103,
VIDEO: 104,
FILE: 105,
AT_TEXT: 106,
MERGE: 107,
CARD: 108,
LOCATION: 109,
CUSTOM: 110,
REVOKE_RECEIPT: 111,
C2C_RECEIPT: 112,
TYPING: 113,
QUOTE: 114,
FACE: 115,
ADVANCED_REVOKE: 118,
FRIEND_ADDED: 1201,
OA_NOTIFICATION: 1400,
GROUP_CREATED: 1501,
GROUP_INFO_CHANGED: 1502,
MEMBER_QUIT: 1504,
GROUP_OWNER_CHANGED: 1507,
MEMBER_KICKED: 1508,
MEMBER_INVITED: 1509,
MEMBER_ENTER: 1510,
GROUP_DISMISSED: 1511,
GROUP_MEMBER_MUTED: 1512,
GROUP_MEMBER_CANCEL_MUTED: 1513,
GROUP_MUTED: 1514,
GROUP_CANCEL_MUTED: 1515,
GROUP_ANNOUNCEMENT_UPDATED: 1519,
GROUP_NAME_UPDATED: 1520,
BURN_CHANGE: 1701,
REVOKE: 2101
}
const CHAT_TYPE = {
SINGLE: 'singleChat',
GROUP: 'groupChat'
SINGLE: 1,
GROUP: 3,
NOTIFICATION: 4
}
const MENTION_ALL = {
TEXT: '所有人',
VALUE: 'ALL'
TEXT: '所有人',
VALUE: 'ALL'
}
const CHANGE_MESSAGE_BODAY_TYPE = {
RECALL: 0,
DELETE: 1,
MODIFY: 2
RECALL: 0,
DELETE: 1,
MODIFY: 2
}
export default {
SESSION_MESSAGE_TYPE,
CUSTOM_TYPE,
ALL_MESSAGE_TYPE,
CHAT_TYPE,
MENTION_ALL,
CHANGE_MESSAGE_BODAY_TYPE
SESSION_MESSAGE_TYPE,
CUSTOM_TYPE,
ALL_MESSAGE_TYPE,
CHAT_TYPE,
MENTION_ALL,
CHANGE_MESSAGE_BODAY_TYPE
}

View File

@ -7,6 +7,8 @@ import { onClickOutside } from '@vueuse/core'
/* 组件 */
import PreviewSendImg from '../suit/previewSendImg.vue'
import VueAt from 'vue-at/dist/vue-at-textarea' // for textarea
import * as MessageApi from '@/api/im/message'
import { generateUUID } from '@/utils'
const props = defineProps({
nowPickInfo: {
type: Object,
@ -100,17 +102,21 @@ const sendTextMessage = _.debounce(async () => {
em_at_list: isAtAll.value ? MENTION_ALL.VALUE : _.map(atMembers.value, 'value')
}
}
const imMessageSendReqVO = {
clientMessageId: generateUUID(),
receiverId: nowPickInfo.value.id,
conversationType: nowPickInfo.value.chatType,
contentType: ALL_MESSAGE_TYPE.TEXT,
content: textContent.value
}
//
if (messageQuoteRef.value?.isShowQuoteMsgBox) {
}
textContent.value = ''
messageQuoteRef.value?.clearQuoteContent()
try {
console.log('msgOptions', msgOptions)
// await store.dispatch('sendShowTypeMessage', {
// msgType: ALL_MESSAGE_TYPE.TEXT,
// msgOptions
// })
console.log('imMessageSendReqVO', imMessageSendReqVO)
await MessageApi.sendMessage(imMessageSendReqVO)
} catch (error) {
//handleSDKErrorNotifi(error.type, error.message)
console.log('>>>>>>>发送失败+++++++', error)

View File

@ -2,43 +2,21 @@
import { formatDate } from '@/utils/formatTime'
/* 默认头像 */
import defaultAvatar from '@/assets/imgs/avatar.gif'
/* emits */
const emit = defineEmits(['scroll-message-list', 're-edit-message', 'message-quote'])
const messageData = ref([
{
id: 1,
type: 'text',
isRecall: false,
time: '2024-04-01 12:00:00',
from: '1',
msg: 'Hello, world!',
modifiedInfo: {
operationCount: 1
}
/* props */
const props = defineProps({
messageData: {
type: [Array, Object],
default: () => []
},
{
id: 2,
type: 'text',
isRecall: false,
time: '2024-04-01 12:00:01',
from: '2',
msg: 'Hi, there!',
modifiedInfo: {
operationCount: 0
}
},
{
id: 3,
type: 'text',
isRecall: true,
time: '2024-04-01 12:00:02',
from: '1',
msg: 'Hello, world!',
modifiedInfo: {
operationCount: 0
}
nowPickInfo: {
type: Object,
default: () => ({}),
required: true
}
])
})
const { nowPickInfo } = toRefs(props)
const { messageData } = toRefs(props)
//
const ALL_MESSAGE_TYPE = {
TEXT: 'txt',
IMAGE: 'img',
@ -52,6 +30,7 @@ const ALL_MESSAGE_TYPE = {
}
/* 处理时间显示间隔 */
const handleMsgTimeShow = (time, index) => {
console.log('>>>>>时间显示', time, index)
const msgList = Array.from(messageData.value)
if (index !== 0) {
const lastTime = msgList[index - 1].time
@ -108,10 +87,6 @@ const startplayAudio = (msgBody) => {
audioPlayStatus.playMsgId = ''
})
}
//
const reEdit = (msg) => emit('reEditMessage', msg)
//
const onMsgQuote = (msg) => emit('messageQuote', msg)
</script>
<template>
<div>

View File

@ -5,10 +5,9 @@ import { messageType } from '@/constant/im'
import MessageList from './components/messageList/index.vue'
import InputBox from './components/inputBox/index.vue'
const { push, currentRoute } = useRouter() //
const { query } = useRoute() //
const { CHAT_TYPE } = messageType
const { CHAT_TYPE, ALL_MESSAGE_TYPE } = messageType
/* header 操作 */
const drawer = ref(false) //
const handleDrawer = () => {
@ -25,10 +24,10 @@ const delTheFriend = () => {
}
//
const nowPickInfo = ref({
id: '1',
id: 1,
chatType: CHAT_TYPE.SINGLE,
userInfo: {
nickname: '好友1',
nickname: '芋道源码',
userStatus: '1'
},
groupDetail: {
@ -45,27 +44,40 @@ const groupDetail = computed(() => {
//id
const messageData = computed(() => [
{
type: 'text'
}
])
//getIdInfo
const stopWatchRoute = watch(
() => query,
(routeVal) => {
console.log('>>>>>>>>监听到路由参数变化', routeVal)
if (routeVal) {
// nowPickInfo.value = { ...routeVal }
// loginState.value && getIdInfo(routeVal)
id: 1,
type: ALL_MESSAGE_TYPE.TEXT,
isRecall: false,
time: '1711944000000',
from: '1',
msg: 'Hello, world!',
modifiedInfo: {
operationCount: 1
}
},
{
immediate: true
id: 2,
type: ALL_MESSAGE_TYPE.TEXT,
isRecall: false,
time: '1711944001000',
from: '2',
msg: 'Hi, there!',
modifiedInfo: {
operationCount: 0
}
},
{
id: 3,
type: ALL_MESSAGE_TYPE.TEXT,
isRecall: true,
time: '1711944002000',
from: '1',
msg: 'Hello, world!',
modifiedInfo: {
operationCount: 0
}
}
)
//route
onBeforeRouteLeave(() => {
stopWatchRoute()
})
])
/* 消息相关 */
const loadingHistoryMsg = ref(false) //
const isMoreHistoryMsg = ref(true) //
@ -74,6 +86,10 @@ const notScrollBottom = ref(false) //是否滚动置底
const fechHistoryMessage = (loadType) => {
console.log(loadType)
console.log('加载更多')
loadingHistoryMsg.value = true
setTimeout(() => {
loadingHistoryMsg.value = false
}, 1000)
}
//
const scrollMessageList = (direction) => {
@ -96,37 +112,15 @@ const messageQuote = (msg) => inputBox.value.handleQuoteMessage(msg)
</div>
<div v-else> {{ nowPickInfo.id }}<span style="font-size: 10px">(非好友)</span> </div>
</template>
<!-- 单人展示删除拉黑 -->
<span class="more" v-if="nowPickInfo.chatType === CHAT_TYPE.SINGLE">
<el-dropdown placement="bottom-end" trigger="click">
<svg
width="18"
height="4"
viewBox="0 0 18 4"
fill="none"
xmlns="http://www.w3.org/2000/svg"
>
<circle cx="2" cy="2" r="2" fill="#333333" />
<circle cx="9" cy="2" r="2" fill="#333333" />
<circle cx="16" cy="2" r="2" fill="#333333" />
</svg>
<template #dropdown>
<el-dropdown-menu>
<el-dropdown-item @click="delTheFriend"> 删除好友 </el-dropdown-item>
<!-- <el-dropdown-item @click="addFriendToBlackList">
加入黑名单
</el-dropdown-item> -->
</el-dropdown-menu>
</template>
</el-dropdown>
</span>
</el-header>
<el-main class="chat_message_main">
<el-scrollbar class="main_container" ref="messageContainer">
<div class="innerRef">
<div v-show="isMoreHistoryMsg" class="chat_message_tips">
<div
v-show="messageData?.length && messageData[0].type !== 'inform'"
v-show="
messageData?.length && messageData[0].type !== ALL_MESSAGE_TYPE.OA_NOTIFICATION
"
class="load_more_msg"
>
<el-link
@ -140,13 +134,7 @@ const messageQuote = (msg) => inputBox.value.handleQuoteMessage(msg)
<el-link v-show="loadingHistoryMsg" disabled>消息加载中...</el-link>
</div>
</div>
<MessageList
:nowPickInfo="nowPickInfo"
:messageData="messageData"
@scroll-message-list="scrollMessageList"
@re-edit-message="reEditMessage"
@message-quote="messageQuote"
/>
<MessageList :nowPickInfo="nowPickInfo" :messageData="messageData" />
</div>
</el-scrollbar>
</el-main>