Android 全埋点解决方案(3)

简介: Android 全埋点解决方案

看一下我们自定义的WrapperOnClickListener

/*public*/ class WrapperOnClickListener implements android.view.View.OnClickListener {
    private android.view.View.OnClickListener source;
    WrapperOnClickListener(android.view.View.OnClickListener source) {
        this.source = source;
    }
    @Override
    public void onClick(android.view.View view) {
        //调用原有的 OnClickListener
        try {
            if (source != null) {
                source.onClick(view);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        //插入埋点代码
        SensorsDataPrivate.trackViewOnClick(view);
    }
}

很简单,也是实现系统的OnClickListener方法,然后在执行click的时候插入埋点代码

然后看一下trackViewOnClick方法:

    public static void trackViewOnClick(android.view.View view) {
        try {
            JSONObject jsonObject = new JSONObject();
            jsonObject.put("element_type", view.getClass().getCanonicalName());
            jsonObject.put("element_id", getViewId(view));
            jsonObject.put("element_content", getElementContent(view));
            Activity activity = getActivityFromView(view);
            if (activity != null) {
                jsonObject.put("activity", activity.getClass().getCanonicalName());
            }
            SensorsDataAPI.getInstance().trackClick("$AppClick", jsonObject);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

比较简单,但是有两个参数是需要注意的:

  • element_type 控件的类型,比如TextView、Button
  • element_id 控件的id,页面全路径 + 控件id即可表示唯一标示了

然后就是trackClick方法了

    public void trackClick(@androidx.annotation.NonNull String eventName, @androidx.annotation.Nullable JSONObject properties) {
        try {
            JSONObject jsonObject = new JSONObject();
            jsonObject.put("event", eventName);
//            jsonObject.put("device_id", mDeviceId);
            JSONObject sendProperties = new JSONObject(mDeviceInfo);
            String act = properties.get("activity").toString();
            //获取页面的参数
            if (act.contains("SecondActivity")) {
                SecondActivity activity = (SecondActivity) SensorsDataPrivate.getCurrentActivity();
                String userId = activity.getIntent().getStringExtra("userId");
                properties.put("userId", userId);
            }
            if (properties != null) {
                SensorsDataPrivate.mergeJSONObject(properties, sendProperties);
            }
            jsonObject.put("extras", sendProperties);
            jsonObject.put("eventTime", System.currentTimeMillis());
            jsonObject.put("sessionId", UUID.randomUUID().toString().replace("-", ""));
            Log.i(TAG, SensorsDataPrivate.formatJson(jsonObject.toString()));
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

跟页面的埋点基本差不太多,来看看数据:

{
  "event": "$AppClick",
  "extras": {
    "app_name": "TrackDemo",
    "screen_width": 1440,
    "screen_height": 2621,
    "app_version": "1.0",
    "os_version": "10",
    "model": "Android SDK built for x86",
    "manufacturer": "Google",
    "element_type": "androidx.appcompat.widget.AppCompatButton",
    "element_id": "button",
    "element_content": "点击传值跳转",
    "activity": "com.yechaoa.trackdemo.ui.MainActivity"
  },
  "eventTime": 1603279293756,
  "sessionId": "b8d1aa32039a4fb1b2ece7772d60cd0e"
}

可以看到数据都是正常的,但是element_content字段并不能太过依赖,为什么呢,因为这个是获取的控件文本,不是所有的控件都有文本的,比如没有描述的ImageView、CheckBox等。


这些都是系统的控件,那如果是我们自定义View怎么办呢,正好演示一下事件的手动埋点。

        button2.setOnClickListener {
            val jsonObject = JSONObject()
            jsonObject.put("element_type", "androidx.constraintlayout.widget.ConstraintLayout")
            jsonObject.put("element_id", "自定义id")
            jsonObject.put("element_content", "自定义内容")
            jsonObject.put("id", 1234)
            jsonObject.put("activity", this.javaClass.canonicalName)
            SensorsDataAPI.getInstance().trackClick("AppClick", jsonObject)
        }

看一下数据:

 {
      "event":"AppClick",
      "extras":{
        "app_name":"TrackDemo",
        "screen_width":1440,
        "screen_height":2621,
        "app_version":"1.0",
        "os_version":"10",
        "model":"Android SDK built for x86",
        "manufacturer":"Google",
        "element_type":"androidx.constraintlayout.widget.ConstraintLayout",
        "element_id":"自定义id",
        "element_content":"自定义内容",
        "id":1234,
        "activity":"com.yechaoa.trackdemo.ui.SecondActivity",
        "userId":"111"
      },
      "eventTime":1603283095128,
      "sessionId":"addbc3d8335244328fcd352221a7a11d"
    }

加入自定义view监测不到的情况下,就可以用这种方式来手动埋点。


除了正常的单个控件的点击事件之外,还有列表的item click事件、还有RatingBar等等,限于篇幅就不细说了,原理都是相通的,具体可以查看Demo。



Demo:https://github.com/yechaoa/TrackDemo


目录
相关文章
|
XML Java Android开发
Android Studio开发APP启动程序时开屏简单动画效果快速有效解决方案
Android Studio开发APP启动程序时开屏简单动画效果快速有效解决方案
1337 0
Android Studio开发APP启动程序时开屏简单动画效果快速有效解决方案
|
3天前
|
安全 编译器 API
Android HAL深入探索(5): 调试HAL报错与解决方案
Android HAL深入探索(5): 调试HAL报错与解决方案
6 1
|
1月前
|
JSON Android开发 数据格式
android 使用GSON 序列化对象出现字段被优化问题解决方案
android 使用GSON 序列化对象出现字段被优化问题解决方案
|
8月前
|
IDE Java 开发工具
Android Gradle plugin requires Java 11 to run. You are currently using Java 1.8的解决方案
Android Gradle plugin requires Java 11 to run. You are currently using Java 1.8的解决方案
|
7月前
|
Android开发
Android Studio 控制台中文乱码,解决方案都在这里了,完美解决
Android Studio 控制台中文乱码,解决方案都在这里了,完美解决
|
8月前
|
Android开发
Android 中ViewPager嵌套RecyclerView出现滑动冲突的解决方案
Android 中ViewPager嵌套RecyclerView出现滑动冲突的解决方案
706 0
|
8月前
|
Android开发
Android > Project with path ‘:audiovisualize‘ could not be found in project ‘:app‘. 异常解决方案
Android > Project with path ‘:audiovisualize‘ could not be found in project ‘:app‘. 异常解决方案
42 0
|
9月前
|
网络协议 Linux Android开发
Android部分手机4G网第一次请求很慢(wifi正常)解决方案
Android部分手机4G网第一次请求很慢(wifi正常)解决方案
256 0
|
10月前
|
Android开发 C++
Android 6.0以上手机报 so: has text relocations 问题的终极解决方案
Android 6.0以上手机报 so: has text relocations 问题的终极解决方案
|
安全 Java 定位技术
Android 校正系统时间的三种解决方案
Android 校正系统时间的三种解决方案
1546 0