laitimes

Application and practice of AOP technology in the client

author:Flash Gene

Programming ideas

面向过程编程(Procedure Oriented Programming),即OPP

Focus on algorithms, function calls with different functions. Commonly used C language

Pros: Task breakdown, step-by-step

面向对象编程(Object Oriented Programming),即OOP

Split a feature/problem into different object modules. Commonly used C++, Java

Advantages: modular structure, easy to expand and maintain

It seems that OOP programming has been able to solve most of our problems, so why do we need AOP programming?

What is AOP(What)

Definition of AOP

The abbreviation of Aspect Oriented Programming, that is, "Aspect Oriented Programming", is a technology that realizes the unified maintenance of program functions through pre-compilation and runtime dynamic agents.

AOP is a continuation of OOP, a hot topic in software development, and a derivative paradigm of functional programming. AOP can be used to isolate each part of the business logic, so that the coupling degree between the parts of the business logic can be reduced, the reusability of the program can be improved, and the development efficiency can be improved.

AOP is actually a supplement to OOP, which distinguishes classes horizontally, while AOP adds specific code to objects vertically. To put it more figuratively, AOP is like a knife that can slice the whole process according to the tangent points you want, so that the whole process is clearly visible.

Application and practice of AOP technology in the client

Several concepts in AOP

  • Aspect: A slice is a collection of entry points and notifications. -------> custom slice file
  • PointCut: Entry points are those connection points that are filtered by using some specific expressions to cut into the Advice.
  • Advice notification: A notification is a code implementation method injected into a tangent. ---> implementation method
  • Joint Point: All target methods are connection points.
  • Weaving: This is the process of injecting slice code into the target using AJC at compile time, and generating a mixed .class code.
  • In a word: the process of injecting code (advices) into joint points

Introduction to AspectJ

AspectJ is a framework for section-oriented programming that extends the java language and defines the syntax for implementing AOP. We know that the javac compilation tool is used by default when compiling .java files to .class files, and AspectJ will have a set of compilation tools that conform to the java bytecode encoding specification to replace javac, and when compiling .java files into .class files, some code will be dynamically inserted to achieve unified processing of a specific class of things.

AOP's arsenal of tools:

  • AspectJ:
  • A seamless extension of the JavaTM language for facet programming (for Android).
    • Introduction: Can weave into all classes, supports compile-time and load-time code injection, is simple to write, and is powerful. Requires compilation with the AJC compiler, which is an extension of the Java compiler with all its features.
  • Javassist for Android:
  • An Android port of Javassist, a well-known java library for bytecode manipulation.
    • Introduction: It can weave into most classes, generate at runtime, reduce unnecessary generation overhead, and reduce the overhead of generating subclasses by writing the slice logic to bytecode, so as not to generate too many subclasses. Slice logic is added to the runtime, resulting in performance overhead.
  • DexMaker:
  • Java API for generating code at compile time or runtime.
    • Introduction: Support for compile-time and load-time code injection, API running on Android Dalvik VM, written in Java, to dynamically generate DEX bytecode.
  • ASMDEX:
  • An ASM-like bytecode manipulation library that runs on the Android platform and manipulates Dex bytecode.
    • Introduction: All classes can be weaved, and compile-time and load-time code injection is supported. To modify bytecode, you need to be familiar with class files, and the writing process is complicated.

Why AOP?

Aop is like a knife that hits the code you want when the program is running, why do you do it? Or what are the benefits of doing it?

Take a chestnut:

When I need to know that the program has been executed to a certain step, or observe certain parameters, logging has become a necessary debug method. The normal practice is to add a log to each method, if there is only one file or the project is very small, there is no problem, but when the amount of engineering code is very large, such a method is very inefficient. With the AOP method, you can cut the methods and properties in the class horizontally, and you can even care about what class you are. This horizontal slicing method can complete better monitoring and debugging, and deal with problems in a unified manner, which is a good supplement to OOP.

How to apply it in the client

  1. Integration via Gradle
  2. The project path is gradle
  3. classpath 'com.hujiang.aspectjx:gradle-android-plugin-aspectjx:2.0.4'
  4. Gradle in the app directory
  5. apply plugin: 'android-aspectjx'
  6. Define the annotation class
  7. @Retention(RetentionPolicy.RUNTIME)

    @Target({ElementType.CONSTRUCTOR, ElementType.METHOD})

    public @interface CheckLogin {

    }

  8. Define tangential points and implement notifications based on specific business scenarios
  9. /**

    * @author : created by lixuecheng

    * Date :2019/11/13 16:00

    * VERSION : 1.0

    * DES : 切面检查登录

    **/

    @Aspect

    public class CheckLoginAspect {

    The entry point slice expression

    @Pointcut("execution(@com.joyoungsoft.aopchecklogin.annotation.CheckLogin * *(..))")

    public void methodAnnotated() {}

    notice

    /**

    ** 前置通知(Before)、

    ** 后置通知(AfterReturning)、

    ** 异常通知(AfterThrowing)、

    ** 最终通知(After)

    ** 环绕通知(Around)

    **

    **/

    @Around("methodAnnotated()")

    public void aroundJoinPoint(ProceedingJoinPoint joinPoint) {

    Context context = getContext(joinPoint.getThis());

    String sessionkey = "";

    if(context != null) {

    sessionkey = (String)SPUtils.get(context, Cons.SP_SESSION_KEY, "");

    } else {

    return;

    }

    // String sessionkey = (String)SPUtils.get(context, Cons.SP_SESSION_KEY, "");

    If(sessioncaseinvalid(sessionki)) {

    joinPoint.proceed();

    } else {

    showHintDialog();

    }

    }

    private Context getContext(Object object) {

    if (object instanceof Activity) {

    return (Activity) object;

    } else if (object instanceof Fragment) {

    Fragment fragment = (Fragment) object;

    return fragment.getActivity();

    } else if (object instanceof View) {

    View view = (View) object;

    return view.getContext();

    }

    return null;

    }

    }

  10. Cut in at the attachment point
  11. @CheckLogin

    @Override

    public void onCheckedChanged(RadioGroup group, @IdRes int checkedId) {

    Toggle the bottom navigation logic

    }

Analysis of several important scenarios (Where)

Performance monitoring: Records the call time before and after a method is called, and alarms are generated for the method execution is too long or times out.

Traceless burying: Add the corresponding statistical code where the burying needs to be buried to build a non-intrusive burying statistical system

Logging: Records system logs before and after method execution.

Permission verification: Before the method is executed, verify whether the method has the permission to execute the current method, and if not, an exception is thrown to be executed, which is captured by the service code.

Hotfix: NetEase has a hotfix based on the AOP framework

Global Login Session Verification: Handles user identity verification in a unified manner

Interface stabilization: prevents the interface from being double-clicked, also known as stabilization, and directly cuts to the onclick method of controlling the view

Write at the end

Brief description of the principle of AOP

AspectJ is essentially writing slices in a specific language, compiled by its own syntax compilation tool, the ajc compiler, to generate a new proxy class that augments the business class.

Here's what AspectJ does:

  1. First, take out all the file names from the file list, read the files, and analyze them.
  2. Scan facet files containing aspects;
  3. Intercept matching JoinPoints based on the rules defined in the slice;
  4. Continue to read the rules defined by the slice, weaving the slice with different strategies depending on around or before.

other

  1. Not every link point needs to be annotated, and the demo uses only one of them
  2. Among the notification methods, Before, After, and Around are the most commonly used in the front-end, and they are different in implementation principle.
  3. The implementation of Before and After is to insert the notification method directly on the original code, and the Around notification method is through the proxy and closure method
  4. The expression in the entry point, we generally apply execution, and there are other ways
  5. As for the principle of convenience, the more in-depth ones are dynamic agents, static agents, interceptions, reflections, etc

Two minor problems

  1. Can the pointcut expression be combined with the regular expression to try something else?
  2. What happens to annotation a static method?
  3. You can try it~

Author: aLi

Source-WeChat public account: Joyoung technical team

Source: https://mp.weixin.qq.com/s/Vg4bWbIgx9ayxsymH-M84A