# 系统消息组件

本文讲解V5系统中发送消息相关的内容,本文你能知道:

  • 如何调用接口发送消息
  • 如何新增消息类型
  • 如何自定义新的消息

# 快速开始:开发示例

我们以一个发送系统消息的Java后端代码为例,想要发送消息,只需要: 1)注入UserMessageManager实体Bean对象 2)调用UserMessageManager接口的sendXXX方法

# 特别注意!

此方式发送消息,只能在pc端进行显示或pc右下角消息盒子弹出。并不会推送到移动端! 若需要推送消息到移动端,建议使用cip消息集成: https://open.seeyon.com/book/ctp/ji-cheng-chang-jing/xiao-xi-ji-cheng.html

private UserMessageManager userMessageManager;
public void setUserMessageManager(UserMessageManager userMessageManager){
    this.userMessageManager = userMessageManager;
}

public void sendMessage(){
	MessageContent msgContent = new MessageContent("消息内容");
	Long sendUserId = AppContext.currentUserId();
	List<MessageReceiver> msgReceivers = xxx;
    userMessageManager.sendSystemMessage(msgContent, ApplicationCategoryEnum.taskManage, sendUserId, msgReceivers);
}

# UserMessageManager使用说明

UserMessageManager有几种接口形式:

# 接口类型

/**
  * 发送系统消息,发送给单个接收者
  * @param content  消息体 
  * @param messageCategroy 消息所属应用分类 在com.seeyon.ctp.common.constants.ApplicationCategoryEnum中定义 
  * @param senderId  发送者ID 
  * @param receiver  接收者 
  * @param messageFilterArgs  消息转移的参数,与对应的UserMessageFilter对应 
  * @see com.seeyon.ctp.common.constants.ApplicationCategoryEnum 
  * @throws MessageException 
  */ 
void sendSystemMessage(MessageContent content, 
    ApplicationCategoryEnum messageCategroy, long senderId, 
    MessageReceiver receiver, Object... messageFilterArgs) throws MessageException; 

/** 
  * 发送系统消息,发送给多个接收者
  * @param content  消息体 
  * @param messageCategroy 
  *                       消息所属应用分类 
  *                     在com.seeyon.ctp.common.constants.ApplicationCategoryEnum中定义 
  * @param senderId  发送者ID 
  * @param receivers  接收者 
  * @param messageFilterArgs  消息转移的参数,与对应的UserMessageFilter对应 
  * @see com.seeyon.ctp.common.constants.ApplicationCategoryEnum 
  * @throws MessageException 
  */ 
  void sendSystemMessage(MessageContent content, 
    ApplicationCategoryEnum messageCategroy, long senderId, 
    Collection  receivers,  Object...  messageFilterArgs)  throws 
        MessageException; 

/** 
  * 发送系统消息,使用指定的时间发送给多个接收者
  * @param content   消息体 
  * @param messageCategroy 
  *                       消息所属应用分类 
  *                       在com.seeyon.ctp.common.constants.ApplicationCategoryEnum中定义 
  *                       如果是插件,需要在插件定义文件中配置applicationCategory属性 
  * @param senderId  发送者ID 
  * @param creationDate  发送时间 
  * @param receivers  接收者 
  * @param messageFilterArgs  消息转移的参数,与对应的UserMessageFilter对应 
  * @see com.seeyon.ctp.common.constants.ApplicationCategoryEnum 
  * @throws MessageException 
  */ 
void sendSystemMessage(MessageContent content, int messageCategroy, 
    long senderId, Date creationDate, 
    Collection receivers, Object... messageFilterArgs) 
    throws MessageException;

# 注意事项

  • 如果MessageContent相同,接收者为多人的情况下,禁止通过for-each 方式调用sendSystemMessage方法发送消息 ;而应该使用多接收者的接口。
  • 如果MessageContent的Subject是动态的,比如:处理协同的状态,通过消息定义来解决。

# 参数说明

# MessageContent构造消息体

MessageContent 消息体,主要封装国际化key以及参数。国际化内容放在各插件的中的国际化文件中,不需要在消息组件中的国际化文件中增加。

几种构造方法说明: 方式一: new MessageContent(String key, Object... param) 方式二:MessageContent.get(String key, Object... param) 方式三:new MessageContent() .add(String key, Object... params)

例如:

MessageContent messageContent = new MessageContent() 
      .add("col.send", subject, sender.getName()) 
      .add("col.agent") 
      .setBody(bodyContent, bodyType, bodyCreateDate);

设置正文,主要用于email的正文:MessageContent.setBody(String bodyContent, String bodyType, Date bodyCreateDate) 设置重要程度:1普通,2重要,3非常重 要:MessageContent.setImportantLevel(Integer)

# MessageReceiver 消息接收者

MessageReceiver 消息接收者,主要封装关联主体对象id、接收人Id、链接类型及链接参数

几种构造方法说明:

  • 每个接收者的链接地址都不一样,通过for-each单个构造 MessageReceiver MessageReceiver.get(Long referenceId, long receiverId, String linkType, String... linkParam)
  • 一个接收者,但没有连接 MessageReceiver MessageReceiver.get(Long referenceId, long receiverId)
  • 多个接收者,一样的链接 List get(Long referenceId, List receiverIds, String linkType, String... linkParam)
  • 多个接收者,都没有链接 List get(Long referenceId, List receiverIds)

# 消息通道(第三方系统接收平台消息)

当第三方系统(sms,email,rtx,gke)需要接收协同平台消息时,可以使用消息展现通道。

只需实现一个消息接口, 系统就可以把外部的应用集成进来,在集成端可以接收系统 的所有消息,如在线消息,协同,会议,计划等,在系统启动前和用户个人设置中均可以配置。

# 消息通道开发步骤

接口名称:interface MessagePipeline 需要开发继承此接口进行相关代码实现。

/**RTXMessagePipeline是开发示例,项目上可以根据场景自行命名class类名**/
public class RTXMessagePipeline implements MessagePipeline

接口必须实现的方法如下:

方法定义 返回值 备注
getName() String 消息展现通道的系统标示,注意不要重复,有数字字母 下划线构成,如:pc,sms,email,rtx,gke getShowName() string 消息展现通道的显示名称 isAvailability() boolean 该通道是否可用,可以控制是否需要消息展现
isAllowSetting(User currentUser) String 是否允许用户在“个人设置-消息提示设置”中进行配 置; 如:短信提示,需要后台管理员授权,并且设置了个人 的手机号码,人员是当前登录者,允许配置返回 null, 否则返回提示信息(注意国际化)
getAllowSettingCategory() List 得到哪些应用类别可以配置(参考 ApplicationCategoryEnum), 如果采用系统默认, 请直接返回 null 如果不允许配置请参考 isAllowSetting(User currentUser)
invoke(Message[] messages) void 在此方法中处理消息,把消息集成到外系统 getSortId() int 排序号,从 0 开始
isDefaultSend() boolean 默认是否发送,如果为 false,则个人需要在“个人设 置-消息提示设置”中进行配置
isShowSetting() boolean 如果 isDefaultSend 设置为false,则个人需要设置为true

在完成接口的实现后,将实现类注册到系统

<bean id="rtxMessagePipeline" class="com.seeyon.v3x.plugin.rtx.message.RTXMessagePipeline"/>

系统启动时查看ctp.log等系统日志文件,能看到如下加载信息,则代表pc、email和rtx三个消息通道实现加载成功。

[main] INFO MessagePipelineManagerImpl:68 - 加载消息展现通道:[pc, email, rtx]

# 消息通道代码示例

新建消息通道类,继承并实现MessagePipeline接口,编写接口下的方法实现:

public class RTXMessagePipeline implements MessagePipeline {
    // 处理消息
    public void invoke(Message[] messages) {
        for (Message message: messages) {
            try {
                String remoteURL = message.getRemoteURL();
                String userName = message.getReceiverMember().getLoginName();
                RTXNotifyValueBean value = new RTXNotifyValueBean();
                String content = message.getContent();
                value.title = message.getSenderMember().getName();
                // ...
                rtxSendNotifyManager.sendNotify(value);
            } catch (Throwable e) {
                log.error("", e);
            }
        }
    }
    // 该通道是否可用
    public boolean isAvailability() {
        return SystemEnvironment.hasPlugin("rtx");
    }
    // 消息展现通道的系统标示
    public String getName() {
        return "rtx";
    }
    // 默认是否发送
    public boolean isDefaultSend() {
        return false;
    }
    // 排序号
    public int getSortId() {
        return 6;
    }
}

注:标准产品对不同端不同场景均建立了Pipeline实现类,项目开发过程中可以参考进行定制开发。

1695657443198.png

创建人:het
修改人:zhuling