iOS开发初学者入门 | 第⑩章:在真机上运维管理

互联网事件响应接口

重中之重用以处理网络转移事件,接口定义在
AVIMClientEventHandler,主要函数为:

  /**
   * 实现本方法以处理网络断开事件
   */
  public abstract void onConnectionPaused(AVIMClient client);

  /**
   * 实现本方法以处理网络恢复事件
   */
  public abstract void onConnectionResume(AVIMClient client);

在网络中断的事态下,全数的消息收发和对话操作都会晤世难点。

通过 AVIMClient.setClientEventHandler(AVIMClientEventHandler handler)
可以设定全局的 Client伊夫ntHandler。

用浏览器打开http://developer.apple.com(见图10-1)

多少个相当紧要的回调接口

从地方的事例中得以见到,要接到到旁人给你发送的音讯,须要重载
AVIMMessageHandler 类。从 v2 版起初,LeanCloud IM SDK
多量行使回调来报告操作结果,不过对于有个别被动的音信公告,则照旧采取接口来兑现的,蕴含:

  • 当前网络出现变化
  • 对话中有新的音信
  • 对话中有新成员参预
  • 对话中有成员离开
  • 被特邀出席某对话
  • 被踢出对话

LeanCloud IM SDK 内部采取了二种接口来响应这么些事件。

Provisioning
Portal有四片段:Certificates、Identifiers、Devices、Profiles,把那页参与收藏夹,因为大家今后会不时用到那些页面。

出殡消息

树立好对话之后,要发送音讯是很不难的:

AVIMMessage message = new AVIMMessage();
message.setContent("hello");
conversation.sendMessage(message, new AVIMConversationCallback() {
  @Override
  public void done(AVException e) {
    if (null != e) {
      // 出错了。。。
      e.printStackTrace();
    } else {
      Logger.d("发送成功,msgId=" + message.getMessageId());
    }
  }
});

好了,这样一条新闻就发送过去了。但是难点来了,对于「Bob」而言,他怎么才能采纳旁人发给他的新闻吧?

图10-2 Developer Portal

文件音信(AVIMFileMessage)

AVIMTypedMessage
子类,用来发送带附件的消息,开发者可以用它来发送「离线文件」。对于此类消息,LeanCloud
IM SDK 内部会先把公文上传到 LeanCloud 文件存储服务器(自带 CDN
成效),然后把公文元数据(url,文件大小等等)放在音讯包内发送到
LeanCloud 实时通讯服务端。其构造函数注解为:

// 传入本地文件路径,构造消息对象
public AVIMFileessage(String localPath) throws FileNotFoundException, IOException;
// 传入本地文件,构造消息对象
public AVIMFileMessage(File localFile) throws FileNotFoundException, IOException;
// 传入 AVFile 实例,构造消息对象
public AVIMFileMessage(AVFile file);

与公事音信看似,文件音讯也辅助附带文本和其它自定义属性,可以经过如下方法添加
/ 获取越多音信:

  • String getText() / void setText(String text)
  • Map<String, Object> getAttrs() / void setAttrs(Map<String,
    Object> attr);

出殡文书音讯的以身作则代码为:

String localZipfilePath;
try {
  AVIMFileMessage message = new AVIMFileMessage(localZipfilePath);
  message.setText("这是你要的文档");
  conversation.sendMessage(message, new AVIMConversationCallback() {
    @Override
    public void done(AVException e) {
      if (null != e) {
        // 出错了。。。
        e.printStackTrace();
      } else {
        Logger.d("message sent");
      }
    }
  });
} catch (Exception ex) {
}

选拔到那样音信之后,开发者可以通过以下办法,获取到文件元数据(size
等)和二个分包二进制数据的 AVFile 对象:

  • AVFile getAVFile() 方法会重临七个二进制文件的 AVFile
    实例,之后方可因而 AVFile 来成功多少下载只怕其余操作,具体可以参见
    AVFile
    说明
  • String getFileUrl() 方法会重返二进制文件的 url
  • long getSize() 方法会再次回到二进制文件的实际尺寸(单位:byte)
  • Map<String, Object> getFileMetaData()
    可以获取二进制文件的任何元数据音信。

点击右上角的Member
Center,输入你的苹果开发者帐号密码,然后登录(见图10-2)。

群组聊天

与前方的单聊类似,群组聊天也急需先创制三个对话(AVIMConversation),然后发送、接收新的音信。

Profiles

借使您的设备已经激活了开发者方式且添加到了Devices中,你就可以创立provisioning
profile了。provisioning
file
列举出什么设备得以运作你的App。把provisioning
profile添加到Xcode,然后检查此设备是不是授权运转App,provisioning
profile用于位置开发和App Store。不过,App Store的provisioning
profile不压制具体的设施。

点击Provisioning Profiles下方的All,接着点击右上角的加号按钮。

选料iOS App
Development,点击Continue(见图10-15)。Development用来在你电脑上运维App,Distribution是留下你的App提交到利用墟市如故群体测试。

图10-15

接下去,从下拉菜单中选择你的施用的 App
ID,点击Continue(见图10-16)。选拔你要运用此provisioning
profile的证书,一大半气象下,你只要求3个可用证书即可。选拔你的证书然后点击Continue。

图10-16 选择App ID

Page 268 | Chapter 10: Running on a Device

接下去,会现出3个您账户下授权设备清单(见图10-17)。采纳你想要测试应用的设施。

图10-17 设备

最后,使用projectNameDevprojectNameAppStore格式来定名profile
name(见图10-18)(例如:MySelfieAppDev)。使用那种格式命名,可以在Xcode中更便于找到provisioning
profile。点击Generate,然后下载profile。

图10-18

Profiles | Page 269

打开浏览器,点击Provisioning
Profile下方的All,接着点击右上角的加号按钮。

选拔App Store点击Continue。从下拉菜单中接纳App的App
ID,点击Continue。采纳证书,点击Continue。命名profile(例如:MySelfieAppStore),然后点击Generate。

下载profile,然后去文件夹中打开你刚刚下载的provisioning
profile。会以.mobileprovision末尾的多个profile(见图10-19)(MySelfieAppDev.mobileprovision和MySelfieAppStore.mobileprovision)。双击那多少个profile即可添加到Xcode,添加成功后,就可以在工程中看出那两个文件了。

图10-19

Page 270 | Chapter 10: Running on a Device

开拓Xcode工程,点击Project
Navigator中的工程名字,艾德itor中会展现出工程的详细音讯。在Team里的下拉菜单中采纳Add
an Account。登录你开发者帐号和密码,接着点击Add(见图10-20)。

图10-20 添加帐号窗口

Profiles | Page 271

关闭Accounts对话框,回到工程详细音讯中来,点击上方名为Info的tab按钮,清空Bundle
Identifier,然后输入上创设App ID时输入的倒序Bundle
ID(例如:com.johnsmith.selfieapp)。

进而选取Build Settings,滑到Code Signing区域,在Code Signing
Identity下方,Debug一栏选取酷派 Developer:你的名字。确保下方全部的iOS
SDK都以一模一样的名字。Release一栏选拔华为Distribution:你的名字。确保全体的iOS SDK都以千篇一律的名字(见图10-21)。

图10-21 Build Settings tab

点击上方General那些tab选项,确认bundle和集团消息是不是科学无误。

打开浏览器,到AppSchool下载App
icons(图10-22)。(那些网址小编一向打不开,小编也不清楚咋回事,一初步以为是被墙了,后来觉得说不定是网站已经倒闭了吗)

图10-22 App icons

Profiles | Page 273

开辟存放icons的公文夹,然后打开Xcode,把文件夹中的图标拖动到Xcode中的Images.xcassets里。

现行,你可以在真机上运维你的顺序了,把您的iOS设备连接到Mac上,点击Xcode顶部iOS
Simulator下拉菜单,接纳iOS device,点击Play按钮(Run)。

即使你在真机上运维大家以前讲解的小应用Selfie,你大概会合到Xcode的警示“process
launch failed:
Security”,这是率先次运维时的警告,打开你的装置(Motorola或iPod等等),点击Trust
from the App
Developer,接着App会向您收获使用视频头的权限。点击Home键,回到桌面,你看会看App的图标已经显示在桌面上了。

恭喜你,今后,你已经成功地在真机上运转应用了。

设若你收到了错误或然警示,不要担心,熟能生巧,到网站上下载源码(那几个网站只怕废掉了),比较学习,多练习三回,直到成功~

Profiles | Page 273

基类:AVIMTypedMessage

具备富媒体音讯的基类,其申明为

//SDK定义的消息类型,LeanCloud SDK 自身使用的类型是负数,所有正数留给开发者自定义扩展类型使用,0 作为「没有类型」被保留起来。
enum AVIMReservedMessageType {
  UnsupportedMessageType(0),
  TextMessageType(-1),
  ImageMessageType(-2),
  AudioMessageType(-3),
  VideoMessageType(-4),
  LocationMessageType(-5),
  FileMessageType(-6);
};

public abstract class AVIMTypedMessage extends AVIMMessage {
  public AVIMTypedMessage();

  public int getMessageType();

  @Override
  public final String getContent();

  @Override
  public final void setContent(String content);
}

做到注册后,就足以进去Member Center。Member
Center中提供了苹果开发者须求的工具、更新,在[https://developer.apple.com/member](https://link.jianshu.com?t=https://developer.apple.com/member)
center/\

center/)注册登录Member Center。Member Center中有局地号称Certifications,
Identifiers, and Pro‐files
,这一部分就是Provisioning
Portal
,控制管理在你付出进度中须求运用的配备和profiles。

分子管理

在询问到聊天室成员之后,可以让用户特邀部分本身的仇敌参预,作为管理员也可以去除一些「可怕」的分子。
参加新成员的 API 如下:

// 假设需要邀请 Alex,Ben,Chad 三人加入对话
List<String> userIds = new ArrayList<String>();
userIds.add("Alex");
userIds.add("Ben");
userIds.add("Chad");
conversation.addMembers(userIds, new AVIMConversationCallback() {
  @Override
  public void done(AVException error) {
    if (null != error) {
      // 加入失败,报错.
      error.printStackTrace();
    } else {
      // 发出邀请,此后新成员就可以看到这个对话中的所有消息了。
      Logger.d("invited.");
    }
  }
});

敬请成功之后,相关方收到公告的时序是那样的:

    操作者(管理员)                    被邀请者                        其他人
1, 发出请求 addMembers
2,                               收到 onInvited 通知
3, 收到 onMemberJoined 通知      收到 onMemberJoined 通知      收到 onMemberJoined 通知

对应地,踢人时的调用 API 是:

List<String> userIds = new ArrayList<String>();
userIds.add("Alex");
conversation.kickMembers(userIds, new AVIMConversationCallback() {
  @Override
  public void done(AVException error) {
    if (null != error) {
      // 失败,报错.
      error.printStackTrace();
    } else {
      // 成功。
      Logger.d("kicked.");
    }
  }
});

踢人时,相关方收到通告的时序如下:

    操作者(管理员)                被踢者                       其他人
1, 发出请求 kickMembers
2,                          收到 onKicked 通知
3, 收到 onMemberLeft 通知                             收到 onMemberLeft 通知

注意!
假若诚邀、踢人操作发生的时候,被特邀者/被踢者当前不在线,那么通告音信并不会被离线缓存,所以他们再上线的时候将不会吸纳布告。

可以用你的名字大概公司名称来注册开发者账户,注册在您个人名下就是个体开发者账户,注册在商行名下需求集团的邓白氏编码和可表明公司的官方文件。邓白氏编码是你公司独一无二的编码,你可以在[https://developer.apple.com/support/ios/](https://link.jianshu.com?t=https://developer.apple.com/support/ios/)
D-U-N-S.php\

D-U-N-S.php)这几个网站上询问越多的新闻。在大部情状下,注册成个人开发者会更简短一些,当你须求的时候,可以把个人开发者账户转换来集团账户。越多音信,请见[https://
developer.apple.com/programs/](
https://
developer.apple.com/programs/)。

音信接收

在 Bob 这一端,要能接收到消息,要求如下几步:

1,举行开端化;

2,完毕本身的 AVIMMessageHandler,响应新新闻到达通知,紧假设之类函数:

public void onMessage(AVIMMessage message, AVIMConversation conversation, AVIMClient client);

对于 汤姆 发过来的音讯,要出示出来,大家只需兑现 onMessage
即可,示例代码如下:

class CustomMessageHandler extends AVIMMessageHandler {
  @Override
  public void onMessage(AVIMMessage message, AVIMConversation conversation, AVIMClient client) {
    // 新消息到来了。在这里增加你自己的处理代码。
    String msgContent = message.getContent();
    Logger.d(conversation.getConversationid() + " 收到一条新消息:" + msgContent);
  }
}

3,进行登录,代码也与发送端一样。

完全代码如下:

// 自定义消息响应类
class CustomMessageHandler extends AVIMMessageHandler {
  @Override
  public void onMessage(AVIMMessage message, AVIMConversation conversation, AVIMClient client) {
    // 新消息到来了。在这里增加你自己的处理代码。
    String msgContent = message.getContent();
    Logger.d(conversation.getConversationid() + " 收到一条新消息:" + msgContent);
  }
}

// application 的初始化部分
public void onCreate(){
  ...
  AVOSCloud.initialize(this,"{{appId}}","{{appKey}}");
  AVIMMessageManager.registerDefaultMessageHandler(new CustomMessageHandler());
  ...
}

// 用户登录部分
AVIMClient imClient = AVIMClient.getInstance("Bob");
imClient.open(new IMClientCallback(){
  @Override
  public void done(AVIMClient client, AVException e) {
    if (null != e) {
      // 出错了,可能是网络问题无法连接 LeanCloud 云端,请检查网络之后重试。
      // 此时聊天服务不可用。
      e.printStackTrace();
    } else {
      // 成功登录,可以开始进行聊天了。
    };
  }
});

注意!
AVIMMessageManager.registerDefaultMessageHandler() 一定要在
AVIMClient.open() 以前调用,否则或许造成服务器发回去的部分新闻丢失。

此章节接下来的有的要求注册开发者账户,你可以在[http://developer.apple.com/programs/ios.\](http://developer.apple.com/programs/ios.)上注册账户
若是你是在校学员,苹果提供了iOS Developer University
Program免费项目,越来越多细节可以在此处找到[http://developer.apple.com/programs/ios/university\](http://developer.apple.com/programs/ios/university)

往群组发送信息

发送信息万分简单,与前边单聊的风貌同样。

笔者们会专注到,AVIMConversation 还有三个发送消息的法门:

public void sendMessage(final AVIMMessage message, final int messageFlag,
      final AVIMConversationCallback callback)

而那里 flag 的定义有如下二种档次:

  • 暂态新闻(AVIMConversation.TRANSIENT_MESSAGE_FLAG)。那种音讯不会被电动保存(以往在历史音讯中无法找到它),也不帮忙延迟接收,离线用户更不会吸收推送公告,所以适合用来做控制协议。譬如聊天进度中「某某正在输入中…」那样的动静音讯,就适合通过暂态信息来发送。
  • 常见新闻(AVIMConversation.NONTRANSIENT_MESSAGE_FLAG)。那种音信就是我们最常用的音信类型,在
    LeanCloud
    云端会自动保存起来,辅助延迟接收和离线推送,今后在历史新闻中得以找到它。
  • 待回执音信(AVIMConversation.RECEIPT_MESSAGE_FLAG)。这也是一种家常信息,只是信息被对方接收之后
    LeanCloud 服务端会发送一个回执公告给发送方(那就是
    AVIMMessageHandler 中
    public void onMessageReceipt(AVIMMessage message, AVIMConversation conversation, AVIMClient client)
    函数被调用的空子)。

点击“Certifications, Identifiers and
Profiles”这一个链接,接着点击“Certificates”链接。

怎么接受富媒体音信

新版 LeanCloud IM SDK 内部封装了对富媒体消息的帮忙,全体富媒体音讯都以从
AVIMTypedMessage 派生出来的。发送的时候可以间接调用
conversation.sendMessage()
函数。在接收端,大家也特地增加了一类回调接口
AVIMTypedMessageHandler,其定义为:

public class AVIMTypedMessageHandler<T extends AVIMTypedMessage> extends MessageHandler<T> {

  @Override
  public void onMessage(T message, AVIMConversation conversation, AVIMClient client);

  @Override
  public void onMessageReceipt(T message, AVIMConversation conversation, AVIMClient client);
}

开发者可以编制自个儿的音信处理 handler,然后调用
AVIMMessageManager.registerMessageHandler(Class<? extends AVIMMessage> clazz, MessageHandler<?> handler)
函数来注册目的 handler。

接收端对于富媒体音讯的公告处理的言传身教代码如下:

class MsgHandler extends AVIMTypedMessageHandler<AVIMTypedMessage> {

  @Override
  public void onMessage(AVIMTypedMessage message, AVIMConversation conversation, AVIMClient client) {
    // 请按自己需求改写
    switch(message.getMessageType()) {
    case AVIMReservedMessageType.TextMessageType:
      AVIMTextMessage textMsg = (AVIMTextMessage)message;
      Logger.d("收到文本消息:" + textMsg.getText() + ", msgId:" + textMsg.getMessageId());
      break;
    case AVIMReservedMessageType.FileMessageType:
      AVIMFileMessage fileMsg = (AVIMFileMessage)message;
      Logger.id("收到文件消息。msgId=" + fileMsg.getMessageId() + ", url=" + fileMsg.getFileUrl() + ", size=" + fileMsg.getSize());
      break;
    case AVIMReservedMessageType.ImageMessageType:
      AVIMImageMessage imageMsg = (AVIMImageMessage)message;
      Logger.id("收到图片消息。msgId=" + imageMsg.getMessageId() + ", url=" + imageMsg.getFileUrl() + ", width=" + imageMsg.getWidth() + ", height=" + imageMsg.getHeight());
      break;
    case AVIMReservedMessageType.AudioMessageType:
      AVIMAudioMessage audioMsg = (AVIMAudioMessage)message;
      Logger.id("收到音频消息。msgId=" + audioMsg.getMessageId() + ", url=" + audioMsg.getFileUrl() + ", duration=" + audioMsg.getDuration());
      break;
    case AVIMReservedMessageType.VideoMessageType:
      AVIMVideoMessage videoMsg = (AVIMAudioMessage)message;
      Logger.id("收到视频消息。msgId=" + videoMsg.getMessageId() + ", url=" + videoMsg.getFileUrl() + ", duration=" + videoMsg.getDuration());
      break;
    case AVIMReservedMessageType.LocationMessageType:
      AVIMLocationMessage locMsg = (AVIMLocationMessage)message;
      Logger.id("收到位置消息。msgId=" + locMsg.getMessageId() + ", latitude=" + locMsg.getLocation().getLatitude() + ", longitude=" + locMsg.getLocation().getLongitude());
      break;
    }
  }

  @Override
  public void onMessageReceipt(AVIMTypedMessage message, AVIMConversation conversation, AVIMClient client) {
  }
}
MsgHandler msgHandler = new MsgHandler();
AVIMMessageManager.registerMessageHandler(AVIMTypedMessage.class, msgHandler);

LeanCloud IM SDK 内部音信分发的逻辑是那般的:对于收到的任一新消息,SDK
内部都会先解析新闻的类型,根据项目找到开发者为这一品类注册的拍卖
handler,然后逐一调用那个 handler 的 onMessage
函数。若是没有找到专门处理这一门类音信的 handler,就会传递给
defaultHandler 处理。

那样一来,在开发者为 TypedMessage(及其子类) 钦命了尤其的
handler,也内定了大局的 defaultHandler
了的时候,即便发送端发送的是通用的 AVIMMessage 音讯,那么接受端就是
AVIMMessageManager.registerDefaultMessageHandler()中钦定的 handler
被调用;如若发送的是 AVIMTypedMessage(及其子类)的新闻,那么接受端就是
AVIMMessageManager.registerMessageHandler()中指定的 handler 被调用。

Devices

Provisioning
Portal的第壹局地是Devices。不大概小说拿个iOS设备就来真机测试你的施用,测试机需求注册。开发者可以每年注册最多100台测试设施,若是这些设备被移除了,就再也无法添加回来了。Devices部分包含了装有可以使用开发者账户的装备,我们采纳一串唯一的串码UDID来波及设备。

点击Devices下方的All,然后点击右上角的加号按钮。

咱俩须要取得装备的UDID(见图10-14),获取UDID的点子是,先把设备链接到Mac上,运维Xcode,设备连接上后,打开Xcode,选用顶部菜单Window
–>
Devices,出现设备窗口,从右侧栏中选择iOS设备,那时iOS设备上会弹出是或不是信任那台计算机(Trust
This
Computer)的唤醒,点击信任(Trust)。UDID就会在Identifier后面,复制UDID,然后打开浏览器。

把UDID粘贴到输入框中,给这一个设备命名(见图10-14),点击Continue。

图10-14

Devices | Page 267

对话成员变动响应接口

驷马难追用于处理对话中成员变动的风云,接口定义在
AVIMConversationEventHandler,首要函数为:

  /**
   * 实现本方法以处理聊天对话中的参与者离开事件
   *
   * @param members 离开的参与者
   * @param kickedBy 踢人者,自愿退出的情况下踢人者就是参与者
   */
  public abstract void onMemberLeft(AVIMClient client,
      AVIMConversation conversation, List<String> members, String kickedBy);

  /**
   * 实现本方法以处理聊天对话中的参与者加入事件
   *
   * @param members 加入的参与者
   * @param invitedBy 邀请人,有可能是加入的参与者本身
   */
  public abstract void onMemberJoined(AVIMClient client,
      AVIMConversation conversation, List<String> members, String invitedBy);

  /**
   * 实现本方法来处理当前用户被踢出某个聊天对话事件
   *
   * @param kickedBy 踢出你的人
   */
  public abstract void onKicked(AVIMClient client, AVIMConversation conversation,
      String kickedBy);

  /**
   * 实现本方法来处理当前用户被邀请到某个聊天对话事件
   *
   * @param conversation 被邀请的聊天对话
   * @param operator 邀请你的人
   */
  public abstract void onInvited(AVIMClient client, AVIMConversation conversation,
      String operator);

通过
AVIMMessageManager.setConversationEventHandler(AVIMConversationEventHandler handler)
可以设置全局的 Conversation伊夫ntHandler。

图10-1 developer.apple.com

盛开聊天室

盛开聊天室(也叫暂态对话)可以用于很多地点,譬如弹幕、直播等等。在
LeanCloud IM SDK
中,开放聊天室是一类万分的群组,它也协理创造、参预/踢出成员等操作,音讯记录会被保留并可供获取;与平日群组不等同的地点具体浮现为:

  • 不协理查询成员列表,你能够经过有关 API 查询在线人数;
  • 不协助离线新闻、离线推送布告等职能;
  • 未曾成员进入、离开的通报;
  • 壹个用户三回登录只好参与七个开放聊天室,出席新的盛开聊天室后会自动离开原先的聊天室;
  • 参预后半钟头内断网重连会活动进入原聊天室,超过这么些时间则需求重新参加;

Identifiers

Provisioning
Portal的第3某个是Identifiers,在Certificates下方。Identifiers是用来管理App的ID的。有点类似葡萄牙人的社保号,逐个App都有友好无比的App
ID。

要开创3个App ID,大家第1要右侧的侧面栏中点击App
ID,然后点击右上角的加号按钮,出现创立App
ID的界面(见图10-12)。Name一栏中输入App ID
Selfie,不要选择下方列出的特殊符号。App ID Prefix一栏空着,勾选Explicit
App ID。Bundle
ID那有的用到部分倒序的艺术书写,就像在浏览器地址栏中输入网址,只可是顺序是相反的。不用采取图片中的Bundle
ID,例子中的Bundle ID是没用的。输入你协调的Bundle
ID,确保使用以下格式:com.domain.app(例如:com.johnsmith.selfieapp)。

图10-12 创建App ID

Identifiers | Page 265

Bundle ID会进入Xcode中,当您向App Store提交App时,会审查Bundle ID。App
Services,你可以为您的拔取添加卓殊的劳动。点击Continue。须求你再次确认App
ID,即使各项都不利点击Submit。那样,App ID和Bundle
ID都创设已毕了(见图10-13)。

图10-13

Page 266 | Chapter 10: Running on a Device

下载和安装

可以到 LeanCloud
官方下载点下载
LeanCloud IM SDK v2 本子。将下载到的 jar 包参预工程即可。

Page 257

图像新闻(AVIMImageMessage)

AVIMFileMessage
子类,专门用来发送图像和附带文本的以次充好音讯,其构造函数注解为:

// 传入本地文件路径,构造消息对象
public AVIMImageMessage(String localPath) throws FileNotFoundException, IOException;
// 传入本地文件,构造消息对象
public AVIMImageMessage(File localFile) throws FileNotFoundException, IOException;
// 传入 AVFile 实例,构造消息对象
public AVIMImageMessage(AVFile file);

发送图像音信的示范代码为:

String localImagePath;
try {
  AVIMImageMessage message = new AVIMImageMessage(localImagePath);
  message.setText("你说我好看不?");
  conversation.sendMessage(message, new AVIMConversationCallback() {
    @Override
    public void done(AVException e) {
      if (null != e) {
        // 出错了。。。
        e.printStackTrace();
      } else {
        Logger.d("message sent");
      }
    }
  });
} catch (Exception ex) {
}

接受到那般信息随后,开发者可以通过如下方法,获取到多少图像元数据(width,height,图像
size)和贰个暗含图像数据的 AVFile 对象:

  • int getWidth() 方法会再次来到图像的急剧(单位:pixel)
  • int getHeight() 方法会重临图像的惊人(单位:pixel)
  • AVFile getAVFile() (继承自
    AVIMFileMessage)方法会再次回到一个图像文件的 AVFile 实例
  • String getFileUrl() (继承自 AVIMFileMessage)方法会再次来到图像文件的
    url
  • long getSize() (继承自
    AVIMFileMessage)方法会重回图像文件的骨子里尺寸(单位:byte)
  • String getText() (继承自
    AVIMFileMessage)方法会重返随图像一起发送的文件音讯。
  • Map<String, Object> getFileMetaData() (继承自
    AVIMFileMessage)可以博得图像的任何元数据消息。

在这一章节,你将学会怎么着在真机上运转你的App,你将学会怎么创设证书、注册你的测试设施,设置你的App
ID和provisioning
profiles。那章节将介绍和陶冶部分融合为一,所以在看这一章节时,要确保打开Xcode,边看边操作。

一定的文书聊天

咱俩先从最简易的环节下手,看看怎么用 LeanCloud IM SDK v2
兑现一对一文本拉扯。

Certificates

首先局地是Certificates.在您运营App时,Certificates用来认同你的身价。唯一的certificate就像你的签字,那样可以范围其余人在未经你同意的事态下向App
Store提交App。

开拓Certificate部分后,你会看到七个浅米灰入口(见图10-3)。右边是一排选项,Pending代表您日前正值利用的片段certificate,Development
certificates表示用于地方电脑上的证书,Production certificates是用在App
Store上的。

图10-3 Certificates

Certificates | Page 259

点击右上角的加号按钮,采纳iOS App
Development,然后点击Continue继续。接着见面世
率领,让您想创建的申明的连串(见图10-4)。接纳iOS App Development
box,点击孔蒂nue。向导接下来会让您创制CS奥德赛(Certificate Signing
Request),CS汉兰达是创立Certificate的二个口径。

图10-4 New certificate

Page 260 | Chapter 10: Running on a Device

想要成立CS兰德酷路泽,大家第二要打开你Mac中的Keychain
Access这么些应用程序。点击Mac屏幕右上角的Spotlight搜索图标,输入keychain
Access
,然后点击搜索出来的第四个挑选。Keychain
Access运转后会列出您日前计算机上装有的certificates。点击顶部菜单栏中的Keychain
Access,然后采用Certificate Assistant –> Request a Certificate From
a Certificate Authority(见图10-5)。

图10-5 Keychain Access App

接着显示器上会出现图10-6的初叶。填写email和common name,CA Email
address这一栏空着,然后勾选“Saved to
disk”,点击Continue。拔取存放证书的文本夹,然后保留。今后归来浏览器继续Provisioning
Portal。

图10-6 向导Wizard

Certificates | Page 261

创造好CS中华V后,点击浏览器中Continue按钮(见图10-7)。

图10-7

接下去要求您上传CS卡宴文件。点击Choose
File按钮,找到.certSigningRequest文件(见图10-8)。

图10-8 CSR

Page 262 | Chapter 10: Running on a Device

接下去点击Generate,向导起首创办证书。证书创设好后,会产出贰个Download按钮(见图10-9)。点击Download下载证书,开发Downloads文件夹,双击刚刚下载的ios_development.cer文本,那样就把文件添加到你的keychain中了。

图10-9 下载certificate

Certificates | Page 263

再一次打开浏览器,点击右边的All选项。用于App
Store的第3个证书也要求创建。再一次点击右上角的加号按钮,采用“App Store
and Ad
Hoc”点击Continue(见图10-10)。CSHaval成立界面那时会弹出来,这五回,你用上次已经创建好的CSTiguan就能够了。点击孔蒂nue。

图10-10 选择“App Store and Ad Hoc”选项

点击Choose
File按钮选取从前创立好的.certSigningRequest,点击Generate按钮。出现Download下载按钮,点击Download下载新的声明(见图10-11)。双击*ios_distribution.cer
*文本即可添加到keychain中。然后重新打开浏览器。

图10-11

Page 264 | Chapter 10: Running on a Device

文本新闻(AVIMTextMessage)

AVIMTypedMessage 子类,表示一般的文件音讯,其申明为

public class AVIMTextMessage extends AVIMTypedMessage {
  public String getText();
  public void setText(String text);

  public Map<String, Object> getAttrs();
  public void setAttrs(Map<String, Object> attr);
}

可以见到,对于文本新闻,首要的属性有 textattr 五个,通过不难的
getter/setter 就可以访问到。要发送文书新闻,示例代码为:

AVIMTextMessage message = new AVIMTextMessage();
message.setText("hello");
conversation.sendMessage(message, new AVIMConversationCallback() {
  @Override
  public void done(AVException e) {
    if (null != e) {
      // 出错了。。。
      e.printStackTrace();
    } else {
      Logger.d("message sent.");
    }
  }
});

真机上测试App要求登记开发者账户(Apple Developer
account)(将来苹果已经允许开发者没有帐号也能在真机上运维了,笔者写那本书的时候,苹果的国策还从未开放给全部人。),将App发表到App
Store上也急需以此账户。Apple Developer
Program为开发者提供了新式版本的iOS和OSX,注册开发者帐号可以见见WWDC中的摄像。WWDC全称Worldwide
Developer Conference,每年在San
Francisco举行。苹果集团会在WWDC上公告新的产品和软件,注册开发者仍是可以拿到尤其的技术协理,每年要求上缴99法郎,那将是你一笔划算的投资。

创设开放聊天室

和平日的群组类似,建立一个绽放聊天室也是很简单的,只是在
AVIMClient.createConversation(conversationMembers, name, attributes, isTransient, callback)
中大家需求传入 isTransient=true 选项。例如:

Map<String, Object> attr = new HashMap<String, Object>();
attr.put("type", ConversationType_Group);
imClient.createConversation(clientIds, name, attr, true, new AVIMConversationCreatedCallback() {
  @Override
  public void done(AVIMConversation conversation, AVException e) {
    if (null != conversation) {
      // 成功了,进入聊天室
      Intent intent = new Intent(currentActivity, ChatActivity.class);
      Intent.putExtra(“conversation”, conversation);
      currentActivity.startActivity(intent);
    }
  }
});

创建成功之后,我们就可以进来聊天界面了。开放聊天室的任何操作,都与普通群组操作一样。

Page 258 | Chapter 10: Running on a Device

登录

倘诺聊天发起方名叫 Tom,为直观起见,大家运用用户名来作为 clientId
登录聊天系统(LeanCloud 云端只须要 clientId
在动用内唯一即可,具体用什么样数据由应用层决定),代码如下:

AVIMClient imClient = AVIMClient.getInstance("Tom");
imClient.open(new IMClientCallback(){
  @Override
  public void done(AVIMClient client, AVException e) {
    if (null != e) {
      // 出错了,可能是网络问题无法连接 LeanCloud 云端,请检查网络之后重试。
      // 此时聊天服务不可用。
      e.printStackTrace();
    } else {
      // 成功登录,可以开始进行聊天了(假设为 MainActivity)。
      Intent intent = new Intent(currentActivity, MainActivity.class);
      currentActivity.startActivity(intent);
    };
  }
});

摄像音信(AVIMVideoMessage)

AVIMFileMessage
子类,专门用来发送录制和附带文本的鱼目混珠消息,其构造函数注脚为:

// 传入本地文件路径,构造消息对象
public AVIMVideoMessage(String localPath) throws FileNotFoundException, IOException;
// 传入本地文件,构造消息对象
public AVIMVideoMessage(File localFile) throws FileNotFoundException, IOException;
// 传入 AVFile 文件,构造消息对象
public AVIMVideoMessage(AVFile file);

发送视频音信的以身作则代码为:

String localVideoPath;
try {
  AVIMVideoMessage message = new AVIMVideoMessage(localVideoPath);
  message.setText("敢不敢跟我比一比");
  conversation.sendMessage(message, new AVIMConversationCallback() {
    @Override
    public void done(AVException e) {
      if (null != e) {
        // 出错了。。。
        e.printStackTrace();
      } else {
        Logger.d("message sent");
      }
    }
  });
} catch (Exception ex) {
}

收取到这么音信随后,开发者可以可以透过如下方法,获取到几何视频元数据(时长
duration、录像 size)和一个带有摄像数据的 AVFile 对象:

  • double getDuration() 方法会重临视频的长短(单位:秒)
  • AVFile getAVFile() (继承自
    AVIMFileMessage)方法会重返三个摄像文件的 AVFile 实例
  • String getFileUrl() (继承自 AVIMFileMessage)方法会再次来到录像文件的
    url
  • long getSize() (继承自
    AVIMFileMessage)方法会重回录制文件的莫过于尺寸(单位:byte)
  • String getText() (继承自
    AVIMFileMessage)方法会重回随摄像一起发送的文本新闻。
  • Map<String, Object> getFileMetaData() (继承自
    AVIMFileMessage)可以获取录像的此外元数据音讯。

怎么着伸张自身的富媒体音讯

继承于
AVIMTypedMessage,开发者也得以伸张自个儿的富媒体音讯。其必要和步骤是:

  • 达成新的音讯类型,继承自 AVIMTypedMessage。这里需求留意两点:
    • 在 class 上加码一个 @AVIMMessageType(type=123) 的
      Annotation,具体音信类型的值(123)由开发者本人说了算(LeanCloud
      内建的信息类型应用负数,全数正数都留下给开发者扩充使用)。
    • 在音信内部属性上要增添 @AVIMMessageField(name=””) 的
      Annotation,name
      为可选字段在宣称字段属性,同时自定义的字段要有对应的
      getter/setter 方法。
  • 调用
    AVIMMessageManager.registerAVIMMessageType(Class<? extends AVIMTypedMessage> messageType)
    函数举行项目注册
  • 调用
    AVIMMessageManager.registerMessageHandler(Class<? extends AVIMMessage> clazz, MessageHandler<?> handler)
    函数举行新闻处理 handler 注册。

AVIMTextMessage 的源码如下,可供参考:

@AVIMMessageType(type = -1)
public class AVIMTextMessage extends AVIMTypedMessage {

  @AVIMMessageField(name = "_lctext")
  String text;
  @AVIMMessageField(name = "_lcattrs")
  Map<String, Object> attrs;

  public String getText() {
    return this.text;
  }

  public void setText(String text) {
    this.text = text;
  }

  public Map<String, Object> getAttrs() {
    return this.attrs;
  }

  public void setAttrs(Map<String, Object> attr) {
    this.attrs = attr;
  }
}

收起群组音讯

接过贰个群组的音信,与接收单聊的消息也是同等的。

支撑富媒体的闲聊新闻

地点的代码演示了什么样发送简单文本音信,可是今后的交互格局已经更多种化,图像、语音、视频已是格外普遍的新闻类型。v2
版的 LeanCloud IM SDK 已经可以很好地扶助这几个富媒体音讯,具体表达如下:

确立对话

假使我们要跟「Bob」这些用户展开聊天,我们先创设多少个会话,代码如下:

List<String> clientIds = new ArrayList<String>();
clientIds.add("Tom");
clientIds.add("Bob");

// 我们给对话增加一个自定义属性 type,表示单聊还是群聊
// 常量定义:
// int ConversationType_OneOne = 0; // 两个人之间的单聊
// int ConversationType_Group = 1;  // 多人之间的群聊
Map<String, Object> attr = new HashMap<String, Object>();
attr.put("type", ConversationType_OneOne);

imClient.createConversation(clientIds, attr, new AVIMConversationCreatedCallback() {
  @Override
  public void done(AVIMConversation conversation, AVException e) {
    if (null != conversation) {
      // 成功了,这时候可以显示对话的 Activity 页面(假定为 ChatActivity)了。
      Intent intent = new Intent(this, ChatActivity.class);
      Intent.putExtra(“conversation”, conversation);
      startActivity(intent);
    }
  }
});

确立的「对话」在控制台怎么查看

如您所见,大家创立一个对话的时候,指定了成员(汤姆 和
鲍勃)和二个附加的属性({type: 0})。这几个多里胥存到云端后,你在
控制台 -> 存储 -> 数据 里面会看到,_Conversation
表中追加了一条记下,新记录的 m 属性值为["Tom", "Bob"]attr
属性值为{"type":0}。如您所料,m 属性就是对应着成员列表,attr
属性就是用户扩张的额外属性值(以目的的样式储存)。

查询在线人数

通过 AVIMConversation.getMemberCount()
方法可以实时查询开放聊天室的在线人数。示例代码如下:

conversation.getMemberCount(new AVIMConversationMemberCountCallback(){
  @Override
  public void done(Integer memberCount, AVException e) {
    if (null != e) {
      // 出错了:(
    } else {
      // 成功,此时 memberCount 的数值就是实时在线人数
    }
  }
});

新闻响应接口

器重用以处理新新闻到达事件,接口定义在
MessageHandlerAVIMMessageHandler
是贰个空的落到实处类,大家相应通过重载 AVIMMessageHandler
的连锁办法来形成音讯处理。紧要的艺术有:

  // 收到新的消息
  @Override
  public void onMessage(AVIMMessage message, AVIMConversation conversation);

  // 自己发送的消息已经被对方接收
  @Override
  public void onMessageReceipt(AVIMMessage message, AVIMConversation conversation, AVIMClient client);

通过 AVIMMessageManager.registerDefaultMessageHandler(handler)
可以安装全局的 MessageHandler。

笔者们落到实处那三类接口,就足以处理全数的通告新闻了。示例代码如下:

class CustomNetworkHandler extends AVIMClientEventHandler {
  @Override
  public void onConnectionPaused(AVIMClient client) {
    // 请按自己需求改写
    Logger.d("connect paused");
  }

  @Override
  public void onConnectionResume(AVIMClient client) {
    // 请按自己需求改写
    Logger.d("connect resume");
  }
}

class CustomConversationHandler extends AVIMConversationEventHandler {
  public private Context gContext = null;
  private void toast(String str) {
    Toast.makeText(gContext, str, Toast.LENGTH_SHORT).show();
  }
  private void toast(Context context, String str) {
    Toast.makeText(context, str, Toast.LENGTH_SHORT).show();
  }

  @Override
  public void onMemberLeft(AVIMClient client, AVIMConversation conversation, List<String> members, String kickedBy) {
    // 请按自己需求改写
    toast(MsgUtils.nameByUserIds(members) + " left, kicked by " + MsgUtils.nameByUserId(kickedBy));
    //注:MsgUtils 是一个辅助类,nameByUserIds 用来将 userId 转换成用户名
  }

  @Override
  public void onMemberJoined(AVIMClient client, AVIMConversation conversation, List<String> members, String invitedBy) {
    // 请按自己需求改写
    toast(MsgUtils.nameByUserIds(members) + " joined , invited by " + MsgUtils.nameByUserId(invitedBy));
    //注:MsgUtils 是一个辅助类,nameByUserIds 用来将 userId 转换成用户名
  }

  @Override
  public void onKicked(AVIMClient client, AVIMConversation conversation, String kickedBy) {
    // 请按自己需求改写
    toast("you are kicked by " + MsgUtils.nameByUserId(kickedBy));
  }

  @Override
  public void onInvited(AVIMClient client, AVIMConversation conversation, String operator) {
    // 请按自己需求改写
    toast("you are invited by " + MsgUtils.nameByUserId(operator));
  }
};

class CustomMsgHandler extends AVIMMessageHandler {
  @Override
  public void onMessage(AVIMMessage message, AVIMConversation conversation, AVIMClient client) {
    // 请按自己需求改写
    String msgContent = message.getContent();
    Logger.d(conversation.getConversationid() + " 收到一条新消息:" + msgContent);
  }

  @Override
  public void onMessageReceipt(AVIMMessage message, AVIMConversation conversation, AVIMClient client) {
    // 请按自己需求改写
    Logger.d("发往对话 " + conversation.getConversationid() + " 的消息 "+ message.getMessageId() +" 已被接收");
  }
}

// 设置事件响应接口
AVIMClient.setClientEventHandler(new CustomNetworkHandler());
AVIMMessageManager.setConversationEventHandler(new CustomConversationHandler());
AVIMMessageManager.registerDefaultMessageHandler(new CustomMsgHandler());

创设群组

和单聊类似,建立二个五人聊天的群组也是很粗略的。例如:

Map<String, Object> attr = new HashMap<String, Object>();
attr.put("type", ConversationType_Group);
imClient.createConversation(clientIds, attr, new AVIMConversationCreatedCallback() {
  @Override
  public void done(AVIMConversation conversation, AVException e) {
    if (null != conversation) {
      // 成功了!
      Intent intent = new Intent(currentActivity, ChatActivity.class);
      Intent.putExtra(“conversation”, conversation);
      currentActivity.startActivity(intent);
    }
  }
});

得逞未来,大家就可以进入聊天界面了。

地理地方新闻(AVIMLocationMessage)

AVIMTypedMessage
子类,帮忙发送地理地方音信和附带文本的交集消息,其声称为:

public class AVIMLocationMessage extends AVIMTypedMessage {
  public String getText();
  public void setText(String text);

  public Map<String, Object> getAttrs();
  public void setAttrs(Map<String, Object> attr);

  public AVGeoPoint getLocation();
  public void setLocation(AVGeoPoint location);
}

与公事音讯看似,地理地方音信只是扩张了多个 AVGeoPoint 的 Location
属性。要发送地点新闻的示范代码为:

AVIMLocationMessage message = new AVIMLocationMessage();
message.setText("快点过来!");
message.setLocation(new AVGeoPoint(15.9, 56.4));
conversation.sendMessage(message, new AVIMConversationCallback() {
  @Override
  public void done(AVException e) {
    if (null != e) {
      // 出错了。。。
      e.printStackTrace();
    } else {
      Logger.d("message sent");
    }
  }
});

接过到那般的音讯随后,开发者可以取得到实际的地理地方数据。

节奏新闻(AVIM奥迪oMessage)

AVIMFileMessage
子类,专门用来发送语音和附带文本的老婆当军新闻,其构造函数注脚为:

// 传入本地文件路径,构造消息对象
public AVIMAudioMessage(String localPath) throws FileNotFoundException, IOException;
// 传入本地文件,构造消息对象
public AVIMAudioMessage(File localFile) throws FileNotFoundException, IOException;   
// 传入 AVFile 实例,构造消息对象
public AVIMAudioMessage(AVFile file);

出殡音频音信的示范代码为:

String localAudioPath;
try {
  AVIMAudioMessage message = new AVIMAudioMessage(localAudioPath);
  message.setText("听听我唱的小苹果:)");
  conversation.sendMessage(message, new AVIMConversationCallback() {
    @Override
    public void done(AVException e) {
      if (null != e) {
        // 出错了。。。
        e.printStackTrace();
      } else {
        Logger.d("message sent");
      }
    }
  });
} catch (Exception ex) {
}

接到到那般新闻之后,开发者可以通过如下方法,获取到几何音频元数据(时长
duration、音频 size)和二个分包音频数据的 AVFile 对象:

  • double getDuration() 方法会再次回到音频的长短(单位:秒)
  • AVFile getAVFile() (继承自
    AVIMFileMessage)方法会重返贰个音频文件的 AVFile 实例
  • String getFileUrl() (继承自 AVIMFileMessage)方法会再次回到音频文件的
    url
  • long getSize() (继承自
    AVIMFileMessage)方法会再次来到音频文件的实际上尺寸(单位:byte)
  • String getText() (继承自
    AVIMFileMessage)方法会重返随音频一起发送的公文音讯。
  • Map<String, Object> getFileMetaData() (继承自
    AVIMFileMessage)可以得到音频的任何元数据音信。

启用离线新闻推送(仅对 iOS 平台用户有效)

甭管是单聊照旧群聊,当用户 A
发出消息后,借使目的对话中有局地用户日前不在线,LeanCloud
云端能够提供离线推送的艺术来提醒用户。这一效应暗许是关门的,你可以在
LeanCloud 应用控制埃德蒙顿打开它。开启方法如下:

  • 报到 LeanCloud 应用控制台,选拔正确的运用进入;
  • 采用最上面的「消息」服务,依次点击右侧菜单「实时新闻」->「设置」;
  • 在左边「iOS
    用户离线时的推送内容」下填好您要推送出去的消息内容,保存;

那样 iOS 平台上的用户就足以吸收 Push Notification
了(当然,前提是运用本人申请到了 RemoteNotification
权限,也将科学的推送证书上传到了 LeanCloud 控制台)。

初始化

和 LeanCloud 其他服务一样,实时聊天服务的开始化也是在 Application 的
onCreate 方法中展开的:

public class MyApplication extends Application{

    public void onCreate(){
      ...
      AVOSCloud.initialize(this,"{{appId}}","{{appKey}}");
      ...
    }
}

还要在AndroidManifest.xml中间注脚:

<manifest>
   ...

   <application
        android:name=".MyApplication"
        ....>
        ...

        <service android:name="com.avos.avoscloud.PushService" />

        <receiver android:name="com.avos.avoscloud.AVBroadcastReceiver">
            <intent-filter>
                <action android:name="android.intent.action.BOOT_COMPLETED" />
                <action android:name="android.intent.action.USER_PRESENT" />
            </intent-filter>
        </receiver>
        ...
   </application>

</manifest>

接下去大家要求形成用户登录。

简介

自二〇一八年 LeanCloud
发表实时通讯(IM)服务之后,基于用户反映和工程师对须要的消化和对工作的提炼,前2二十六日正规宣布了「实时通讯2.0
」。设计意见照旧是「灵活、解耦、可构成、可定制」,具体可以参考《实时通讯支出指南》,了解LeanCloud 实时通讯的基本概念和模型。

赢得历史新闻

LeanMessage 会将非暂态消息自动保存在云端,之后开发者可以通过
AVIMConversation 来博取该对话的有着历史新闻。获取历史音信的 API 如下:

String oldestMsgId;
long oldestMsgTimestamp;
conversation.queryMessages(oldestMsgId,oldestMsgTimestamp, limit, new AVIMHistoryMessageCallback(){
  @Override
  public void done(List<AVIMMessage> messages, AVException e) {
    if (null != e) {
      // 出错了:(
    } else {
      // 成功,可以将消息加入缓存,同时更新 UI
    }
  }
});

注意:
得到历史音讯的时候,LeanCloud
云端是从某条音讯开首,往前寻找开发者钦定的 N
条音信,再次回到给客户端。为此,获取历史消息必要传入多个参数:早先新闻的
msgId,开首音信的殡葬时间戳,需要得到的音讯条数。

因而这一 API 拿到的消息就是 AVIMMessage 可能 AVIMTypedMessage
实例数组,开发者可以像之前接受新新闻文告一致处理。

签名和三沙

为了满意开发者对权力和认证的渴求,LeanCloud
还布署了操作签名的体制。大家得以在 LeanCloud
应用控制杜阿拉的「设置」->「应用选项」->「聊天推送」上边勾选「聊天服务签约认证」来启用签名(强烈推荐那样做)。启用后,全体的用户登录、对话成立/出席、邀约成员、踢出成员等操作都亟待表明签名,那样开发者就可以对音信举办充裕的主宰。

客户端那边毕竟该怎么运用呢?大家只需求贯彻 SignatureFactory
接口,然后在用户登录以前,把那些接口的实例赋值给 AVIMClient
即可(AVIMClient.setSignatureFactory(factory))。

设定了 signatureFactory 之后,对于急需鉴权的操作,LeanCloud IM SDK
与服务器端通信的时候都会带上应用自个儿生成的 Signature 音讯,LeanCloud
云端会采用 app 的 masterKey 来评释音讯的管用,保障聊天渠道的平安。

对此 SignatureFactory 接口,我们只必要贯彻这七个函数即可:

  /**
   * 实现一个基础签名方法 其中的签名算法会在SessionManager和AVIMClient(V2)中被使用
   */
  public Signature createSignature(String peerId, List<String> watchIds) throws SignatureException;

  /**
   * 实现AVIMConversation相关的签名计算
   */
  public Signature createConversationSignature(String conversationId, String clientId,
      List<String> targetIds, String action) throws SignatureException;

createSignature
函数会在用户登录的时候被调用,createConversationSignature
会在对话创造/参预、特邀成员、踢出成员等操作时被调用。

你须要做的就是根据前文所述的署名算法已毕签约,其中 Signature
表明如下:

public class Signature {
  public List<String> getSignedPeerIds();
  public void setSignedPeerIds(List<String> signedPeerIds);

  public String getSignature();
  public void setSignature(String signature);

  public long getTimestamp();
  public void setTimestamp(long timestamp);

  public String getNonce();
  public void setNonce(String nonce);
}

其中七个性格分别是:

  • signature 签名
  • timestamp 时间戳,单位秒
  • nonce 随机字符串 nonce
  • signedPeerIds 放行的 clientId 列表,v2 中已经撇开不用

上面的代码突显了依据 LeanCloud
云代码进行签约时,客户端的兑现部分,你能够参照它来成功本人的逻辑完毕:

public class KeepAliveSignatureFactory implements SignatureFactory {
 @Override
 public Signature createSignature(String peerId, List<String> watchIds) {
   Map<String,Object> params = new HashMap<String,Object>();
   params.put("self_id",peerId);
   params.put("watch_ids",watchIds);

   try{
     Object result =  AVCloud.callFunction("sign",params);
     if(result instanceof Map){
       Map<String,Object> serverSignature = (Map<String,Object>) result;
       Signature signature = new Signature();
       signature.setSignature((String)serverSignature.get("signature"));
       signature.setTimestamp((Long)serverSignature.get("timestamp"));
       signature.setNonce((String)serverSignature.get("nonce"));
       return signature;
     }
   }catch(AVException e){
     throw (SignatureFactory.SignatureException) e;
   }
   return null;
 }

  @Override
  public Signature createConversationSignature(String convId, String peerId, List<String> targetPeerIds,String action){
   Map<String,Object> params = new HashMap<String,Object>();
   params.put("self_id",peerId);
   params.put("group_id",convId);
   params.put("group_peer_ids",targetPeerIds);
   params.put("action",action);

   try{
     Object result = AVCloud.callFunction("group_sign",params);
     if(result instanceof Map){
        Map<String,Object> serverSignature = (Map<String,Object>) result;
        Signature signature = new Signature();
        signature.setSignature((String)serverSignature.get("signature"));
        signature.setTimestamp((Long)serverSignature.get("timestamp"));
        signature.setNonce((String)serverSignature.get("nonce"));
        return signature;
     }
   }catch(AVException e){
     throw (SignatureFactory.SignatureException) e;
   }
   return null;
  }
}

LeanCloud IM SDK
专注做好底层的通信服务,有越来越多可以定制化的地点,譬如说:

  • 账户种类和 IM 系统是分手的;
  • 新闻成为离线推送的时候,推送内容开发者是可以定制的;
  • 通过 web hook,开发者能够对音信进行越来越多处理;
  • 聊天进度中通过音讯鉴权机制,开发者可以有越来越多控制;

因为贫乏 UI
组件,实事求是地讲在新用户接入开支或然稍高,然而在事情规模扩充、产品须要变多将来,相信大家会越加喜欢
LeanCloud 那种随意灵活的利用体验,以及稳定飞速的劳动品质。

投入开放聊天室

一经任何极端用户都可以加入开放聊天室。作为开发者,大家可以透过通过特定条件检索到独具开放聊天室,然后允许用户自由出席,其示范代码为:

conversation.join(new AVIMConversationCallback(){
  @Override
  public void done(AVException e) {
    if (null != e) {
      // 出错了:(
    } else {
      // 成功,此时可以进入聊天界面了。。。
      Intent intent = new Intent(currentActivity, ChatActivity.class);
      Intent.putExtra(“conversation”, conversation);
      currentActivity.startActivity(intent);
    }
  }
});

群组音讯免干扰(仅对 iOS 平台用户有效)

不管是单聊依然群聊,对于发往普通的 Conversation
的一般性音信,借使接收方当前不在线,LeanCloud 云端援救通过 Push
Notification
的点子展开提醒。一般景观下这都是很好的,可是假使有个别群组特别活跃,这离线用户就会接受过多的推送,会形成不小的干扰。

对此 LeanCloud IM 服务也同意单个用户来关闭/打开有个别对话的离线推送作用。

追寻群组

不论是单聊,照旧群聊,在 LeanCloud IM SDK
里面都是对话(Conversation)。大家给对话设置了如下三种本性:

  • conversationId,字符串,对话 id,只读,对话创立之后由 LeanCloud
    云端赋予一个大局唯一的 id。
  • creator,字符串,对话成立者 id,只读,标识对话创造者新闻
  • members,数组,对话插足者,那里记录了有着的插手者
  • name,字符串,对话的名字,optional,可用来对于群组命名
  • attributes,Map/Dict,自定义属性,optional,供开发者本人伸张用。

大家提供了尤其的类,来查找一定的群组:通过 imClient.getQuery()
得到二个 AVIMConversationQuery 实例,然后调用
AVIMConversationQuery.wherexxx
多元措施来充实约束规范。例如要物色当前报到用户加入的有着群聊对话,其代码为

// 搜索 Tom 参与的所有群组对话
List<String> clients = new ArrayList<String>();
clients.add("Tom");
AVIMConversationQuery conversationQuery = imClient.getQuery();
conversationQuery.containsMember(clients);

// 之前有常量定义:
// const int ConversationType_OneOne = 0;
// const int ConversationType_Group = 1;
conversationQuery.whereEqualTo("attr.type", ConversationType_Group);

conversationQuery.findInBackground(new AVIMConversationQueryCallback(){
  @Override
  public void done(List<AVIMConversation> conversations, AVException e) {
    if (null != e) {
      // 出错了。。。
      e.printStackTrace();
    } else {
      if (null != conversation) {
        Logger.d("找到了符合条件的 " + conversations.size() + " 个对话");
      } else {
        Logger.d("没有找到符合条件的对话");
      }
    }
  }
});

AVIMConversationQuery 中设置条件的艺术与 AVQuery 类似。这里
conversationQuery.containsMember()
表示对话的积极分子中至少含有那些人口,可用来依据局地成员查找对话;与此类似的还有八个
conversationQuery.withMembers()
则表示有且仅有那些成员,用来依据全部成员查找目标对话;conversationQuery.whereXXX()
多级措施可用来限制对话名称和自定义属性,那里要强调的一些是,对于自定义属性的羁绊规范,属性名一定要以
attr 开端,如上例所示,限定额外的 type 条件的时候须求指定的属性名是
attr.type。具体可以参照其头文件。

Post Author: admin

发表评论

电子邮件地址不会被公开。 必填项已用*标注