Browse Source

Merge branch 'v_2.0.0' of gitee.com:bluexsx/box-im into master

Signed-off-by: blue <825657193@qq.com>
master
blue 2 years ago
committed by Gitee
parent
commit
af28628ef8
  1. 7
      im-platform/src/main/java/com/bx/implatform/controller/GroupMessageController.java
  2. 13
      im-platform/src/main/java/com/bx/implatform/controller/PrivateMessageController.java
  3. 6
      im-platform/src/main/java/com/bx/implatform/listener/GroupMessageListener.java
  4. 5
      im-platform/src/main/java/com/bx/implatform/service/IGroupMessageService.java
  5. 12
      im-platform/src/main/java/com/bx/implatform/service/IPrivateMessageService.java
  6. 37
      im-platform/src/main/java/com/bx/implatform/service/impl/GroupMessageServiceImpl.java
  7. 58
      im-platform/src/main/java/com/bx/implatform/service/impl/PrivateMessageServiceImpl.java
  8. 19
      im-ui/src/components/chat/ChatBox.vue
  9. 10
      im-ui/src/store/chatStore.js
  10. 2
      im-ui/src/view/Home.vue
  11. 2
      im-uniapp/App.vue
  12. 8
      im-uniapp/package.json
  13. 12
      im-uniapp/pages/chat/chat-box.vue
  14. 10
      im-uniapp/store/chatStore.js

7
im-platform/src/main/java/com/bx/implatform/controller/GroupMessageController.java

@ -35,13 +35,6 @@ public class GroupMessageController {
return ResultUtils.success();
}
// todo 删除
@PostMapping("/pullUnreadMessage")
@ApiOperation(value = "拉取未读消息", notes = "拉取未读消息")
public Result pullUnreadMessage() {
groupMessageService.pullUnreadMessage();
return ResultUtils.success();
}
@GetMapping("/loadMessage")
@ApiOperation(value = "拉取消息", notes = "拉取消息,一次最多拉取100条")

13
im-platform/src/main/java/com/bx/implatform/controller/PrivateMessageController.java

@ -36,13 +36,6 @@ public class PrivateMessageController {
return ResultUtils.success();
}
@PostMapping("/pullUnreadMessage")
@ApiOperation(value = "拉取未读消息", notes = "拉取未读消息")
public Result pullUnreadMessage() {
privateMessageService.pullUnreadMessage();
return ResultUtils.success();
}
@GetMapping("/loadMessage")
@ApiOperation(value = "拉取消息", notes = "拉取消息,一次最多拉取100条")
@ -57,6 +50,12 @@ public class PrivateMessageController {
return ResultUtils.success();
}
@GetMapping("/maxReadedId")
@ApiOperation(value = "获取最大已读消息的id",notes="获取某个会话中已读消息的最大id")
public Result<Long> getMaxReadedId(@RequestParam Long friendId){
return ResultUtils.success(privateMessageService.getMaxReadedId(friendId));
}
@GetMapping("/history")
@ApiOperation(value = "查询聊天记录", notes = "查询聊天记录")
public Result<List<PrivateMessageVO>> recallMessage(@NotNull(message = "好友id不能为空") @RequestParam Long friendId,

6
im-platform/src/main/java/com/bx/implatform/listener/GroupMessageListener.java

@ -21,11 +21,7 @@ public class GroupMessageListener implements MessageListener<GroupMessageVO> {
@Override
public void process(IMSendResult<GroupMessageVO> result) {
GroupMessageVO messageInfo = result.getData();
// 保存该用户已拉取的最大消息id
if (result.getCode().equals(IMSendCode.SUCCESS.code())) {
String key = String.join(":", RedisKey.IM_GROUP_READED_POSITION, messageInfo.getGroupId().toString(), result.getReceiver().getId().toString());
redisTemplate.opsForValue().set(key, messageInfo.getId());
}
// 空空如也
}
}

5
im-platform/src/main/java/com/bx/implatform/service/IGroupMessageService.java

@ -24,11 +24,6 @@ public interface IGroupMessageService extends IService<GroupMessage> {
*/
void recallMessage(Long id);
/**
* 异步拉取群聊消息通过websocket异步推送
*/
void pullUnreadMessage();
/**
* 拉取消息只能拉取最近1个月的消息一次拉取100条
*

12
im-platform/src/main/java/com/bx/implatform/service/IPrivateMessageService.java

@ -35,10 +35,6 @@ public interface IPrivateMessageService extends IService<PrivateMessage> {
*/
List<PrivateMessageVO> findHistoryMessage(Long friendId, Long page, Long size);
/**
* 异步拉取私聊消息通过websocket异步推送
*/
void pullUnreadMessage();
/**
* 拉取消息只能拉取最近1个月的消息一次拉取100条
@ -48,10 +44,18 @@ public interface IPrivateMessageService extends IService<PrivateMessage> {
*/
List<PrivateMessageVO> loadMessage(Long minId);
/**
* 消息已读,将整个会话的消息都置为已读状态
*
* @param friendId 好友id
*/
void readedMessage(Long friendId);
/**
* 获取某个会话中已读消息的最大id
*
* @param friendId 好友id
*/
Long getMaxReadedId(Long friendId);
}

37
im-platform/src/main/java/com/bx/implatform/service/impl/GroupMessageServiceImpl.java

@ -136,41 +136,6 @@ public class GroupMessageServiceImpl extends ServiceImpl<GroupMessageMapper, Gro
log.info("撤回群聊消息,发送id:{},群聊id:{},内容:{}", session.getUserId(), msg.getGroupId(), msg.getContent());
}
@Override
public void pullUnreadMessage() {
UserSession session = SessionContext.getSession();
List<GroupMember> members = groupMemberService.findByUserId(session.getUserId());
for (GroupMember member : members) {
// 获取群聊已读的最大消息id,只推送未读消息
String key = String.join(":", RedisKey.IM_GROUP_READED_POSITION, member.getGroupId().toString(), session.getUserId().toString());
Integer maxReadedId = (Integer) redisTemplate.opsForValue().get(key);
LambdaQueryWrapper<GroupMessage> wrapper = Wrappers.lambdaQuery();
wrapper.eq(GroupMessage::getGroupId, member.getGroupId()).gt(GroupMessage::getSendTime, member.getCreatedTime())
.ne(GroupMessage::getSendId, session.getUserId()).ne(GroupMessage::getStatus, MessageStatus.RECALL.code());
if (maxReadedId != null) {
wrapper.gt(GroupMessage::getId, maxReadedId);
}
wrapper.last("limit 100");
List<GroupMessage> messages = this.list(wrapper);
if (messages.isEmpty()) {
continue;
}
// 推送
for (GroupMessage message : messages) {
GroupMessageVO msgInfo = BeanUtils.copyProperties(message, GroupMessageVO.class);
IMGroupMessage<GroupMessageVO> sendMessage = new IMGroupMessage<>();
sendMessage.setSender(new IMUserInfo(session.getUserId(), session.getTerminal()));
// 只推给自己当前终端
sendMessage.setRecvIds(Collections.singletonList(session.getUserId()));
sendMessage.setRecvTerminals(Collections.singletonList(session.getTerminal()));
sendMessage.setData(msgInfo);
imClient.sendGroupMessage(sendMessage);
}
// 发送消息
log.info("拉取未读群聊消息,用户id:{},群聊id:{},数量:{}", session.getUserId(), member.getGroupId(), messages.size());
}
}
@Override
public List<GroupMessageVO> loadMessage(Long minId) {
@ -239,7 +204,7 @@ public class GroupMessageServiceImpl extends ServiceImpl<GroupMessageMapper, Gro
sendMessage.setSender(new IMUserInfo(session.getUserId(), session.getTerminal()));
sendMessage.setSendToSelf(true);
sendMessage.setData(msgInfo);
sendMessage.setSendResult(false);
sendMessage.setSendResult(true);
imClient.sendGroupMessage(sendMessage);
// 记录已读消息位置
String key = CharSequenceUtil.join(":", RedisKey.IM_GROUP_READED_POSITION, groupId, session.getUserId());

58
im-platform/src/main/java/com/bx/implatform/service/impl/PrivateMessageServiceImpl.java

@ -30,10 +30,7 @@ import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.List;
import java.util.*;
import java.util.stream.Collectors;
@Slf4j
@ -131,42 +128,6 @@ public class PrivateMessageServiceImpl extends ServiceImpl<PrivateMessageMapper,
}
@Override
public void pullUnreadMessage() {
UserSession session = SessionContext.getSession();
// 获取当前连接的channelId
if (!imClient.isOnline(session.getUserId())) {
throw new GlobalException(ResultCode.PROGRAM_ERROR, "用户未建立连接");
}
List<Friend> friends = friendService.findFriendByUserId(session.getUserId());
if (friends.isEmpty()) {
return;
}
List<Long> friendIds = friends.stream().map(Friend::getFriendId).collect(Collectors.toList());
// 获取当前用户所有未读消息
LambdaQueryWrapper<PrivateMessage> queryWrapper = Wrappers.lambdaQuery();
queryWrapper.eq(PrivateMessage::getRecvId, session.getUserId())
.eq(PrivateMessage::getStatus, MessageStatus.UNSEND)
.in(PrivateMessage::getSendId, friendIds);
List<PrivateMessage> messages = this.list(queryWrapper);
// 上传至redis,等待推送
for (PrivateMessage message : messages) {
PrivateMessageVO msgInfo = BeanUtils.copyProperties(message, PrivateMessageVO.class);
// 推送消息
IMPrivateMessage<PrivateMessageVO> sendMessage = new IMPrivateMessage<>();
sendMessage.setSender(new IMUserInfo(session.getUserId(), session.getTerminal()));
sendMessage.setRecvId(session.getUserId());
sendMessage.setRecvTerminals(Collections.singletonList(session.getTerminal()));
sendMessage.setSendToSelf(false);
sendMessage.setData(msgInfo);
imClient.sendPrivateMessage(sendMessage);
}
log.info("拉取未读私聊消息,用户id:{},数量:{}", session.getUserId(), messages.size());
}
@Override
public List<PrivateMessageVO> loadMessage(Long minId) {
UserSession session = SessionContext.getSession();
@ -233,4 +194,21 @@ public class PrivateMessageServiceImpl extends ServiceImpl<PrivateMessageMapper,
this.update(updateWrapper);
log.info("消息已读,接收方id:{},发送方id:{}", session.getUserId(), friendId);
}
@Override
public Long getMaxReadedId(Long friendId) {
UserSession session = SessionContext.getSession();
LambdaQueryWrapper<PrivateMessage> wrapper = Wrappers.lambdaQuery();
wrapper.eq(PrivateMessage::getSendId, session.getUserId())
.eq(PrivateMessage::getRecvId, friendId)
.orderByDesc(PrivateMessage::getId)
.select(PrivateMessage::getId)
.last("limit 1");
PrivateMessage message = this.getOne(wrapper);
if(Objects.isNull(message)){
return -1L;
}
return message.getId();
}
}

19
im-ui/src/components/chat/ChatBox.vue

@ -462,7 +462,7 @@
let file = this.sendImageFile;
this.onImageBefore(this.sendImageFile);
let formData = new FormData()
formData.append('file', file)
formData.append('file', file)
this.$http.post("/image/upload", formData, {
headers: {
'Content-Type': 'multipart/form-data'
@ -543,7 +543,7 @@
});
},
readedMessage() {
if(this.chat.unreadCount==0){
if (this.chat.unreadCount == 0) {
return;
}
this.$store.commit("resetUnreadCount", this.chat)
@ -557,6 +557,17 @@
method: 'put'
}).then(() => {})
},
loadReaded(fId) {
this.$http({
url: `/message/private/maxReadedId?friendId=${fId}`,
method: 'get'
}).then((id) => {
this.$store.commit("readedMessage", {
friendId: fId,
maxId: id
});
});
},
loadGroup(groupId) {
this.$http({
url: `/group/find/${groupId}`,
@ -646,6 +657,8 @@
this.loadGroup(this.chat.targetId);
} else {
this.loadFriend(this.chat.targetId);
//
this.loadReaded(this.chat.targetId)
}
//
this.scrollToBottom();
@ -683,6 +696,7 @@
width: 100%;
background: #f8f8f8;
border: #dddddd solid 1px;
.el-header {
padding: 5px;
background-color: white;
@ -784,6 +798,7 @@
.send-image-area {
text-align: left;
border: #53a0e7 solid 1px;
.send-image-box {
position: relative;
display: inline-block;

10
im-ui/src/store/chatStore.js

@ -70,13 +70,17 @@ export default {
}
this.commit("saveToStorage");
},
readedMessage(state, friendId) {
readedMessage(state, pos) {
for (let idx in state.chats) {
if (state.chats[idx].type == 'PRIVATE' &&
state.chats[idx].targetId == friendId) {
state.chats[idx].targetId == pos.friendId) {
state.chats[idx].messages.forEach((m) => {
if (m.selfSend && m.status != MESSAGE_STATUS.RECALL) {
m.status = MESSAGE_STATUS.READED
// pos.maxId为空表示整个会话已读
if(!pos.maxId || m.id <= pos.maxId){
m.status = MESSAGE_STATUS.READED
}
}
})
}

2
im-ui/src/view/Home.vue

@ -177,7 +177,7 @@
this.$store.commit("resetUnreadCount", chatInfo)
} else {
//
this.$store.commit("readedMessage", friendId)
this.$store.commit("readedMessage", {friendId:friendId})
}
return;
}

2
im-uniapp/App.vue

@ -119,7 +119,7 @@
store.commit("resetUnreadCount", chatInfo)
} else {
//
store.commit("readedMessage", friendId)
store.commit("readedMessage", {friendId:friendId})
}
return;

8
im-uniapp/package.json

@ -6,16 +6,16 @@
"browser":"chrome",
"env": {
"UNI_PLATFORM": "h5",
"BASE_URL": "http://192.168.43.6:8888",
"WS_URL": "ws://192.168.43.6:8878/im"
"BASE_URL": "http://127.0.0.1:8888",
"WS_URL": "ws://127.0.0.1:8878/im"
}
},
"dev-wx-mini": {
"title": "开发环境-微信小程序",
"env": {
"UNI_PLATFORM": "mp-weixin",
"BASE_URL": "http://192.168.43.6:8888",
"WS_URL": "ws://192.168.43.6:8878/im"
"BASE_URL": "http://127.0.0.1:8888",
"WS_URL": "ws://127.0.0.1:8878/im"
}
},
"prod-h5": {

12
im-uniapp/pages/chat/chat-box.vue

@ -424,6 +424,17 @@
})
}
},
loadReaded(fId) {
this.$http({
url: `/message/private/maxReadedId?friendId=${fId}`,
method: 'get'
}).then((id) => {
this.$store.commit("readedMessage", {
friendId: fId,
maxId: id
});
});
},
readedMessage() {
if (this.chat.type == "GROUP") {
var url = `/message/group/readed?groupId=${this.chat.targetId}`
@ -552,6 +563,7 @@
this.loadGroup(this.chat.targetId);
} else {
this.loadFriend(this.chat.targetId);
this.loadReaded(this.chat.targetId)
}
},
onUnload() {

10
im-uniapp/store/chatStore.js

@ -75,13 +75,17 @@ export default {
}
this.commit("saveToStorage");
},
readedMessage(state, friendId) {
readedMessage(state, pos) {
for (let idx in state.chats) {
if (state.chats[idx].type == 'PRIVATE' &&
state.chats[idx].targetId == friendId) {
state.chats[idx].targetId == pos.friendId) {
state.chats[idx].messages.forEach((m) => {
if (m.selfSend && m.status != MESSAGE_STATUS.RECALL) {
m.status = MESSAGE_STATUS.READED
// pos.maxId为空表示整个会话已读
if(!pos.maxId || m.id <= pos.maxId){
m.status = MESSAGE_STATUS.READED
}
}
})
}

Loading…
Cancel
Save