version

v0.6.5

An overview of the

This article is the second in a series of Matrix series on Tencent’s open source APM framework, and will read the code of matrix-Android-lib. This module mainly builds the Matrix plug-in architecture. Gradle plugin for Matrix

Take a look at the class diagram and an overview of the class’s capabilities.

  • Matrix: Entry to Matrix for the entire framework runtime. It also controls the plug-in life cycle. All plug-ins need to be registered into the Matrix class for unified management
  • AppActiveMatrixDelegate: an Application delegate that can sense the Activity lifecycle and notify the APP when it enters the foreground or exits the backgroundIAppForeground
  • IPlugin: Defines the life cycle and common methods of all plugins
  • IssuePublisher. OnIssueDetectListener: only oneonDetectIssueMethod is called when a problem needs to be reported
  • IAppForeground: Only one method isonForegroundWill beAppActiveMatrixDelegateCall, can sense whether the APP enters the foreground or exits to the background
  • The Plugin: implementIPlugin.ssuePublisher.OnIssueDetectListenerandIAppForeground. It is the parent class of all plug-ins, and has the functions of plug-in life cycle, problem awareness and APP state switch. The concrete implementation isTracePlugin.IOCanaryPlugin.ResourcePlugin.SQLiteLintPluginAnd we’ll look at each of them.

Let’s start with the entry class Matrix.

1. Matrix

This is what we normally initialize with Matrix

Matrix.Builder builder = new Matrix.Builder(this); builder.plugin(new TracePlugin()); builder.plugin(new IOCanaryPlugin()); . [1.1] Matrix Matrix =builder.build(); // see [3.1] matrix.startallplugins ();Copy the code

1.1 Matrix construction method

The builder pattern is used to create Matrix objects, so let’s look at the Matrix construction method without further ado

private Matrix(Application app, PluginListener listener, < plugins > plugins) {// Save the argument passed to builder this.application = app; this.pluginListener = listener; this.plugins = plugins; / / initialize Application proxy objects See [1.2] AppActiveMatrixDelegate. The INSTANCE. The init (application);for// See [2.1] plugin.init(application, pluginListener); // pluginlistener.oninit (plugin); }}Copy the code

And you can see that in the Matrix constructor, it does three things

  1. The first step is to save the parameters passed in the Builder to its own member variables, the most important of which are the ones stored in the HashSetPlugin.
  2. Initialize theAppActiveMatrixDelegateThe proxy object for this Application
  3. Loop through allPluginThe init method of

1.2 AppActiveMatrixDelegate. The init ()

It is worth saying that AppActiveMatrixDelegate this class is an enumeration singleton, do not understand the benefits of enumeration singleton and the difference between several other singleton methods of students, you can baidu, Google, a lot of online articles. We continue to see AppActiveMatrixDelegate. The init ()

// see [1.3] Controller Controller = new Controller(); Public void init(Application Application) {// Ensure that the initialization is done only onceif (isInit) {
            return;
        }
        this.isInit = true; / / get the child thread handler enclosing handler = new handler (MatrixHandlerThread. GetDefaultHandlerThread () getLooper ()); / / to monitor onConfigurationChanged and onLowMemory application. RegisterComponentCallbacks (controller); / / to monitor the activity life cycle application. RegisterActivityLifecycleCallbacks (controller); }Copy the code

You can see in the init () method, application to register the ActivityLifecycleCallbacks and ComponentCallbacks2 both listening, and the two monitoring points to the same Controller object. With these two listening ActivityLifecycleCallbacks has the perceptual Activity of the capability of life cycle and APP activities.

1.3 the Controller

private final class Controller implements Application.ActivityLifecycleCallbacks, ComponentCallbacks2 {@override public void onActivityStarted(Activity Activity) { updateScene(activity); [1.5] onDispatchForeground(getVisibleScene()); } @Override public void onActivityStopped(Activity activity) {if[1.6] onDispatchBackground(getVisibleScene()); (getTopActivityName() == null) { }}... @Override public void onTrimMemory(int level) { MatrixLog.i(TAG,"[onTrimMemory] level:%s", level);
            if(level == TRIM_MEMORY_UI_HIDDEN && isAppForeground) {// Fallback // onDispatchBackground(visibleScene); }}}Copy the code

You can see that Controller is the class that really knows the state of the APP.

1.4 Controller. UpdateScene ()

Private void updateScene(Activity Activity) {visibleScene = activity.getClass().getName(); }Copy the code

1.5 Controller. OnDispatchForeground ()

Private void onDispatchForeground(String visibleScene) {// If APP is visible, no action is takenif(isAppForeground || ! isInit) {return;
        }
        handler.post(new Runnable() {
            @Override
            public void run() {// Change APP state to visible isAppForeground =true;
                synchronized (listeners) {
                    for[Notice about IAppForeground listener: listeners]true); }}}}); }Copy the code

1.6 Controller. OnDispatchBackground ()

Private void onDispatchBackground(String visibleScene) {// If APP is already invisible, do nothingif(! isAppForeground || ! isInit) {return;
        }
        handler.post(new Runnable() {
            @Override
            public void run() {
                isAppForeground = false;
                synchronized (listeners) {
                    for[Notice about IAppForeground listener: listeners]false); }}}}); }Copy the code

2.1 the Plugin. The init ()

After initializing the AppActiveMatrixDelegate object in the constructor of Matrix, plugin.init () is called

@Override public void init(Application app, PluginListener listener) { .... // Change the current state of plugin to PLUGIN_INITED status = PLUGIN_INITED; this.application = app; this.pluginListener = listener; / / to register to see [2.2] AppActiveMatrixDelegate AppActiveMatrixDelegate. The INSTANCE. The addListener (this); }Copy the code

2.2 AppActiveMatrixDelegate. INSTANCE. AddListener (this);

It can be seen that the Plugin registered itself in the AppActiveMatrixDelegate during init, and the Plugin can sense when the state of the APP front and background changes

Public void addListener(IAppForeground listener) {synchronized (listeners) {// AddListeners; }}Copy the code

3.1 Matrix. StartAllPlugins ()

StartAllPlugins this simpler approach is to start all plug-in, Matrix as a plug-in manager also has other similar methods such as stopAllPlugins, destroyAllPlugins

// Start all plug-ins public voidstartAllPlugins() {
        for(Plugin plugin : plugins) { plugin.start(); }}Copy the code

Plugin.onDetectIssue()

Override public void onReportIssue (Issue Issue) {Override public void onReportIssue (Issue Issue) {if (issue.getTag() == null) {
            // set default tag
            issue.setTag(getTag());
        }
        issue.setPlugin(this);
        JSONObject content = issue.getContent();
        // add tag and type for default
        try {
            if(issue.getTag() ! = null) { content.put(Issue.ISSUE_REPORT_TAG, issue.getTag()); }if(issue.getType() ! = 0) { content.put(Issue.ISSUE_REPORT_TYPE, issue.getType()); } content.put(Issue.ISSUE_REPORT_PROCESS, MatrixUtil.getProcessName(application)); content.put(Issue.ISSUE_REPORT_TIME, System.currentTimeMillis()); } catch (JSONException e) { MatrixLog.e(TAG,"json error", e);
        }

        //MatrixLog.e(TAG, "detect issue:%s", issue);
        pluginListener.onReportIssue(issue);
    }
Copy the code

Plugin provides a simple unified data reporting method and encapsulates the reported data into Json strings in a unified format.

Conclusion:

  1. MatrixIt is the portal to the framework and the manager of all plug-ins
  2. All plug-ins need to be inheritedPlugin.PluginIt has the ability to report problems and perceive the status of the APP.

series

  • Tencent Apm framework Matrix source read – Gradle plug-in
  • Tencent Apm framework Matrix source code reading – architecture analysis

The resources

  • recommendedMatrix source complete annotation
  • Matrix Android TraceCanary
  • ————Trace Canary