《插件自助开发——统计类插件》

统计系统

开发者可以准确跟踪用户每次的应用使用,准确统计启动、活跃、留存数据。本文介绍了如何接入SDK的统计服务。

类名和初始化

统计系统的类一般命名为"Analytics+插件名",并且需要遵循InterfaceAnalytics协议

@interface AnalyticsTalkingGame : NSObject <InterfaceAnalytics>

-(void)configDeveloperInfo:(NSMutableDictionary *)cpInfo;

在init方法里,调用configDeveloperInfo:方法
cpInfo参数通过PluginHelper类getParamsInfo从打包工具配置的参数获取
以talkingGame为例

- (id)init {
   if ([super init]) {
      [self configDeveloperInfo:[PluginHelper getParamsInfo]];
    }
   return self;
}

 - (void)configDeveloperInfo:(NSMutableDictionary *)cpInfo {
      OUTPUT_LOG(@"config params:%@",cpInfo);
      self.bDebug = [PluginHelper getDebugModeStatus];
      @try {
          _appID = [cpInfo objectForKey:@"TalkingGameAppID"];
          _channelID = [cpInfo objectForKey:@"TalkingGameChannelID"];
          if (!_appID || !_channelID) {
             OUTPUT_LOG(@"params error!");
             return;
           }
       }
       @catch (NSException *exception) {
            NSLog(@"NSException %@",exception);
       }
 }

InterfaceAnalytics

统计类插件需要实现接口InterfaceAnalytics,接口中没有的方法,开发者可以自定义拓展。在InterfaceAnalytics接口中,有如下函数:

public void startSession();     //开始跟踪用户使用中的打开应用和页面跳转的数据
public void stopSession();      //结束跟踪用户使用中的打开应用和页面跳转的数据
public void setSessionContinueMillis(int millis);   //会话时间间隔
public void setCaptureUncaughtException(boolean isEnabled);     //设置SDK自动获取异常
public void logError(String errorId, String message);       //手动记录错误日志
public void logEvent(String eventId);       //自定义事件
public void logEvent(String eventId, Hashtable<String, String> paramMap);   //自定义事件
public void logTimedEventBegin(String eventId);     //事件开始
public void logTimedEventEnd(String eventId);       //事件结束
public void setDebugMode(boolean paramBoolean);     // 设置调试模式(已废弃)
public String getSDKVersion();      //获取SDK 版本号
public String getPluginVersion();   //获取插件版本号

Session统计

使用数据统计系统需要至少添加以下调用方法,这些调用用于准确跟踪用户每次的 应用使用,是准确统计启动、活跃、留存数据的基础

开始跟踪

- (void)startSession;
建议在viewWillAppear或者viewDidAppear方法里调用startSession用于跟踪用户使用中的打开应用和页面跳转的数据。
以talkingData为例

- (void)startSession {
  OUTPUT_LOG(@"startSession invoked.\n");
  [TalkingData trackPageBegin:@"pageBegin"];
}

结束跟踪

- (void)stopSession;
建议在viewWillDisappear或者viewDidDisappear方法里调用,结束该页面的跟踪行为。
以talkingData为例

- (void)stopSession {
    OUTPUT_LOG(@"stopSession invoked\n");
    [TalkingData trackPageEnd:@"pageEnd"];
}

收集应用错误日志

收集应用的错误日志可帮助您来修正 BUG、改善产品

自动获取异常

- (void)setCaptureUncaughtException:(BOOL)isEnabled;
向setCaptureUncaughtException方法中传入YES(开启自动捕获)或NO(关闭自动捕获), 来控制自动捕获功能的开关。
以talkingData为例

- (void)setCaptureUncaughtException:(BOOL)isEnabled {
   OUTPUT_LOG(@"setCaptureUncaughtException %s invoked\n",isEnabled ? "YES" : "NO");
   [TalkingData setExceptionReportEnabled:isEnabled];
 }

主动传送异常

- (void)logError:(NSString*)errorId withMsg:(NSString*)message;
手动统计应用错误, errorId为错误事件ID, message为错误事件内容。

自定义事件统计

自定义事件可以实现在应用程序中埋点来统计用户的点击行为。同时,自定义事件还支持添加一些描述性的属性参数,使用多对 Key-Value 的方式来进行发送(非必须使用),用来对事件发生时的状况做详尽分析。

自定义事件

- (void)logEvent:(NSString*)eventId - (void)logEvent:(NSString*)eventId withParam:(NSMutableDictionary*)paramMap
开启会话统计,用于跟踪用户离开页面和退出应用的数据。eventId为自定义事件ID,paramMap为事件添加详尽的描述信息,可以更有效的对事件触发的条件和场景做分析。
以talkingData为例

- (void)logEvent:(NSString *)eventId {
    OUTPUT_LOG(@"logEvent %@ invoked.\n", eventId);
    [TalkingData trackEvent:eventId];
}

- (void)logEvent:(NSString *)eventId withParam:(NSMutableDictionary *)paramMap {
    OUTPUT_LOG(@"logEvent %@,%@ invoked.\n", eventId,paramMap);
    //SDK要求,key只能为NSString,value只能为NSString或者NSNumber
    for (NSString *key in [paramMap allKeys]) {
       if (![key isKindOfClass:[NSString class]]) {
           OUTPUT_LOG(@"key is non-conformance");
           return;
       }
    }
    for (id value in [paramMap allValues]) {
       if (![value isKindOfClass:[NSString class]] && ![value isKindOfClass: [NSNumber class]]) {
           OUTPUT_LOG(@"value is non-conformance");
           return;
        }
    }      
    [TalkingData trackEvent:eventId label:eventId parameters:paramMap];
 }

开始事件时间统计

- (void)logTimedEventBegin:(NSString *)eventId
eventId为事件ID

结束事件时间统计

- (void)logTimedEventEnd:(NSString *)eventId;
eventId为事件ID

设置调试模式

- (void)setDebugMode:(BOOL)debug;
已废弃,实现方式参照模板。

获取SDK版本号

- (NSString *)getSDKVersion;
SDK版本是指第三方SDK的版本号,格式可能都不一样,如6.0、1.0.3、2.1.0.4等,这个版本号格式不需要任何改动。

获取插件版本号

- (NSString *)getPluginVersion;
格式『版本序号_SDK版本号』,版本序号从『2.0.0』开始,每次更新+0.0.1

拓展接口

统计玩家账户信息

- (void)setAccount:(NSMutableDictionary *)dic
定义一个玩家单元,更新玩家最新的属性信息。
dic可以传递多个参数,具体参数如下表

参数 是否必传 参数说明
Account_Id Y 游戏中玩家ID
Account_Name Y 游戏中玩家昵称
Account_Type Y 传入帐户的类型(ANONYMOUS匿名,REGISTED自有账号,SINA_WEIBO新浪微博,TENCENT_WEIBO腾讯微博,QQ ,ND91)
Account_Level Y 游戏中玩家等级
Account_Age Y 玩家年龄
Account_Operate Y 账户操作(LOGIN登陆,LOGOUT登出,REGISTER注册)
Account_Gender Y 游戏角色性别(UNKNOWN未知,FEMALE女性,MALE男性)
Server_Id Y 服务器id,若无填“1”,uc请填“0”

以talkingGame为例

- (void)setAccount:(NSMutableDictionary *)dic {
     OUTPUT_LOG(@"setAccount invoked! dic:%@\n",dic);
     @try {
         NSString *accountId = [dic objectForKey:@"Account_Id"];
         NSString *accountName = [dic objectForKey:@"Account_Name"];
         id accountType = [dic objectForKey:@"Account_Type"];
         id accountLevel = [dic objectForKey:@"Account_Level"];
         id accountAge = [dic objectForKey:@"Account_Age"];
         id accountGender = [dic objectForKey:@"Account_Gender"];
         NSString *serverId = [dic objectForKey:@"Server_Id"];
         if (!accountId || !accountName || !accountType || !accountLevel || !accountAge  || !accountGender || !serverId) {
             NSLog(@"error:the parameter is not complete\n");
             return ;
         }
         TDGAAccount *account = [TDGAAccount setAccount:accountId];
         [account setAccountName:accountName];
         [account setAccountType:[accountType intValue]];
         [account setLevel:[accountLevel intValue]];
         [account setGender:[accountGender intValue]];
         [account setAge:[accountAge intValue]];
         [account setGameServer:serverId];
     }
     @catch (NSException *exception) {
         NSLog(@"NSException %@",exception);
     }
}

跟踪玩家充值

跟踪玩家充值现金而获得虚拟币的行为,充入的现金将反映至游戏收入中。
充值过程分两个跟踪阶段:1、发出有效的充值请求;2确认某次充值请求是否完成充值。

跟踪充值请求

- (void)onChargeRequest:(NSMutableDictionary *)dic
在玩家发起充值请求时(例如玩家选择了某个充值包,进入支付流程那一刻)调用 onChargeRequest,并传入该笔交易的唯一订单 ID 和详细信息;
JSONObject info参数如下

参数 是否必传 参数说明
Order_Id Y 订单唯一标示符
Product_Name Y 商品名
Currency_Amount Y 现金数额(元)
Currency_Type Y 请使用国际标准组织 ISO 4217 中规范的 3 位字母代码标记货币类型。点击查看参考例:人民币 CNY;美元 USD;欧元 EUR
Payment_Type Y 支付的途径,最多 16 个字符。例如:“支付宝”“苹果官方”“XX 支付 SDK
Virtual_Currency_Amount Y 虚拟币数值

以talkingGame为例

- (void)onChargeRequest:(NSMutableDictionary *)dic {
     OUTPUT_LOG(@"onChargeRequest invoked! dic:%@\n",dic);
     @try {
         NSString *orderId = [dic objectForKey:@"Order_Id"];
         NSString *productName = [dic objectForKey:@"Product_Name"];
         id currencyAmount = [dic objectForKey:@"Currency_Amount"];
         NSString *currencyType = [dic objectForKey:@"Currency_Type"];
         NSString *paymentType = [dic objectForKey:@"Payment_Type"];
         id virtualCurrencyAmount = [dic objectForKey:@"Virtual_Currency_Amount"];
         if (!orderId || !productName || !currencyAmount || !virtualCurrencyAmount || !currencyType || !paymentType ) {
             NSLog(@"error:the parameter is not complete\n");
             return;
         }
         [TDGAVirtualCurrency onChargeRequst:orderId iapId:productName currencyAmount:[currencyAmount doubleValue] currencyType:currencyType virtualCurrencyAmount:[virtualCurrencyAmount doubleValue] paymentType:paymentType];
   }
   @catch (NSException *exception) {
        NSLog(@"NSException %@",exception);
   }
}

跟踪充值成功

- (void)onChargeSuccess:(NSString *)orderId
在确认玩家支付成功时调用onChargeSuccess:
orderID为需要跟踪完成的订单ID;
talkingGame为例

- (void)onChargeSuccess:(NSString *)orderId {
    OUTPUT_LOG(@"onChargeSuccess %@ invoked!\n",orderId);
    [TDGAVirtualCurrency onChargeSuccess:orderId];
}

跟踪充值失败

- (void)onChargeFail:(NSMutableDictionary *)dic
在确认玩家支付失败时调用 onChargeFail
可以传递多个参数,如订单ID和失败原因:

参数 是否必传 参数说明
Order_Id Y 订单唯一标示符
Fail_Reason Y 失败原因

仅统计支付成功

- (void)onChargeRequest:(NSMutableDictionary *)dic
如果游戏中无法记录充值的发起,那么可以在某次充值成功后,调用onChargeOnlySuccess 方法,来告知一次充值成功的相关信息。
dic可以传递多割参数,具体如下表:

参数 是否必传 参数说明
Order_Id Y 订单唯一标示符
Product_Name Y 商品名
Currency_Amount Y 现金数额(元)
Currency_Type Y 请使用国际标准组织 ISO 4217 中规范的 3 位字母代码标记货币类型。点击查看参考例:人民币 CNY;美元 USD;欧元 EUR
Payment_Type Y 支付的途径,最多 16 个字符。例如:“支付宝”“苹果官方”“XX 支付 SDK
Virtual_Currency_Amount Y 虚拟币数值

跟踪游戏内消费

跟踪游戏中全部使用到虚拟币的消费点,如购买虚拟道具、VIP 服务、复活等;跟踪某物品或服务的耗尽;

虚拟物品购买

- (void)onPurchase:(NSMutableDictionary *)info
在任意消费点发生时尽快调用onPurchase
info参数如下表:

参数 是否必传 参数说明
Item_Id Y 物品标示符
Item_Type Y 物品类型
Item_Count Y 物品数量
Virtual_Currency Y 虚拟金额
Currency_Type Y 支付途径(可用来区分渠道消费)

以talkingGame为例

- (void)onPurchase:(NSMutableDictionary *)info {
     OUTPUT_LOG(@"onPurchase %@ invoked!\n",info);
     @try {
        NSString *item = [info objectForKey:@"Item_Id"];
        id number = [info objectForKey:@"Item_Count"];
        id price = [info objectForKey:@"Virtual_Currency"];
        if (!item || !number || !price) {
           NSLog(@"error:the parameter is not complete\n");
           return;
         }
        [TDGAItem onPurchase:item itemNumber:[number intValue] priceInVirtualCurrency:[price doubleValue]];
      }
     @catch (NSException *exception) {
          NSLog(@"NSException %@",exception);
     }
 }

虚拟物品消耗

- (void)onUse:(NSMutableDictionary *)info
在某个道具/服务被用掉(消失)时尽快调用 onUse
info参数如下表

参数 是否必传 参数说明
Item_Id Y 物品标示符
Item_Type Y 物品类型
Item_Count Y 物品数量
Use_Reason Y 用途说明

以talkingGame为例

- (void)onUse:(NSMutableDictionary *)info {
    OUTPUT_LOG(@"onUse %@ invoked!\n",info);
    @try {
        NSString *item = [info objectForKey:@"Item_Id"];
        id number = [info objectForKey:@"Item_Count"];
        if (!item || !number) {
           NSLog(@"error:the parameter is not complete\n");
           return;
         }
        [TDGAItem onUse:item itemNumber:[number intValue]];
     }
    @catch (NSException *exception) {
         NSLog(@"NSException %@",exception);
     }
  }

虚拟币赠送

- (void)onReward:(NSMutableDictionary *)info
在成功向玩家赠予虚拟币时调用onReward方法并传入相关数据
info参数如下表:

参数 是否必传 参数说明
Item_Id Y 物品标示符
Item_Type Y 物品类型
Item_Count Y 物品数量
Use_Reason Y 用途说明

以talkingGame为例

- (void)onReward:(NSMutableDictionary *)info {
   OUTPUT_LOG(@"onReward %@ invoked!\n",info);
   @try {
       id virtualCurrencyAmount = [info objectForKey:@"Item_Count"];
       NSString *reason = [info objectForKey:@"Use_Reason"];
       if (!virtualCurrencyAmount || !reason ) {
          NSLog(@"error:the parameter is not complete\n");
          return;
        }
       [TDGAVirtualCurrency onReward:[virtualCurrencyAmount doubleValue] reason:reason];
    }
    @catch (NSException *exception) {
        NSLog(@"NSException %@",exception);
    }
 }

关卡

我们提供了一组方法来统计关卡相关的事件。 startLevel、failLevel、finishLevel,其中 startLevel 和 failLevel/finishLevel 方法需要配对出现。

关卡开始

- (void)startLevel:(NSMutableDictionary *)info
在游戏开启新的关卡的时候调用startLevel方法
info参数如下表:

参数 是否必传 参数说明
Level_Id Y 关卡id
Seq_Num Y 关卡顺序

关卡结束

- (void)finishLevel:(NSString *)levelId
在成功过关的时候调用finishLevel方法
levelId为关卡ID

关卡失败

- (void)failLevel:(NSMutableDictionary *)info
在关卡失败的时候调用 failLevel 方法
info参数如下表:

参数 是否必传 参数说明
Level_Id Y 关卡标示符
Fail_Reason Y 失败原因

任务

我们提供了一组方法来统计任务相关的事件。 startTask、failTask、finishTask,其中 startTask 和 failTask/finishTask 方法需要配对出现。

任务开始

- (void)startTask:(NSMutableDictionary *)info;
在游戏开启新的任务的时候调用startTask方法
info参数如下表:

参数 是否必传 参数说明
Task_Id Y 任务id
Task_Type Y 任务类型(GUIDE_LINE主线,MAIN_LINE主线,)

以talkingGame为例

- (void)startTask:(NSMutableDictionary *)info {
    OUTPUT_LOG(@"startTask %@ invoked!\n",info);
    @try {
        NSString *taskId = [info objectForKey:@"Task_Id"];
        if (!taskId) {
           NSLog(@"error:the parameter is not complete\n");
           return;
         }
        [TDGAMission onBegin:taskId];
     }
    @catch (NSException *exception) {
          NSLog(@"NSException %@",exception);
     }
 }

任务完成

- (void)finishTask:(NSString *)taskId;
功能说明:在成功完成任务的时候调用 finishTask方法
taskID为任务ID
以talkingGame为例

- (void)finishTask:(NSString *)taskId {
    OUTPUT_LOG(@"finishTask %@ invoked!\n",taskId);
    [TDGAMission onCompleted:taskId];
}

任务失败

- (void)failTask:(NSMutableDictionary *)info
在任务失败的时候调用 failTask 方法
info参数如下表:

参数 是否必传 参数说明
Task_Id Y 任务标示符
Fail_Reason Y 失败原因

以talkingGame为例

- (void)failTask:(NSMutableDictionary *)info {
    OUTPUT_LOG(@"failTask %@ invoked!\n",info);
    @try {
        NSString* taskId = [info objectForKey:@"Task_Id"];
        NSString* reason = [info objectForKey:@"Fail_Reason"];
        if (!taskId  || !reason) {
            NSLog(@"error:the parameter is not complete\n");
            return;
        }
        [TDGAMission onFailed:taskId failedCause:reason];
    }
    @catch (NSException *exception) {
         NSLog(@"NSException %@",exception);
    }
}