国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 系統 > Android > 正文

AndroidStudio 配置 AspectJ 環境實現AOP的方法

2019-10-22 18:15:24
字體:
來源:轉載
供稿:網友

昨天看了一段android配置aspectj實現AOP的直播視頻,就試著自己配置了一下,可能是因為我自己的AndroidStudio環境的問題,碰到了不少的坑(其實還是因為對gradle理解的不多),但總歸是配置好了,就分享一下。

試了兩種方式,不過項目下的build.gradle,沒什么變化,直接看一下代碼吧:

build.gradle(項目下)

buildscript {  ext {    //android appcompat支持庫版本    androidSupportVersion = '26.1.0'    //編譯的 SDK 版本,如API20    compileSdkVersion = 26    //構建工具的版本,其中包括了打包工具aapt、dx等,如API20對應的build-tool的版本就是20.0.0    buildToolsVersion = "26.0.2"    //兼容的最低 SDK 版本    minSdkVersion = 15    //向前兼容,保存新舊兩種邏輯,并通過 if-else 方法來判斷執行哪種邏輯    targetSdkVersion = 26    //kotlin版本號    kotlin_version = '1.2.10'    kotlinVersion = "org.jetbrains.kotlin:kotlin-stdlib-jre7:$kotlin_version"    appcompatV7 = "com.android.support:appcompat-v7:$androidSupportVersion"    appcompatDesign = "com.android.support:design:$androidSupportVersion"    constraintLayout = 'com.android.support.constraint:constraint-layout:1.0.2'  }  repositories {    google()    jcenter()    mavenCentral()  }  dependencies {    classpath 'com.android.tools.build:gradle:3.0.1'    classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"    classpath 'org.greenrobot:greendao-gradle-plugin:3.2.1'    // NOTE: Do not place your application dependencies here; they belong    // in the individual module build.gradle files    classpath 'org.aspectj:aspectjtools:1.8.13'    classpath 'org.aspectj:aspectjweaver:1.8.13'  }}allprojects {  repositories {    google()    jcenter()    mavenCentral()  }}task clean(type: Delete) {  delete rootProject.buildDir}

看著一大堆,主要就是下面這幾行配置,其他的是我自己項目中用到的,根據自己需要配置就行。

buildscript {  repositories {    mavenCentral()  }  dependencies {    classpath 'org.aspectj:aspectjtools:1.8.13'    classpath 'org.aspectj:aspectjweaver:1.8.13'  }}repositories {  mavenCentral()}

其實這幾行配置在app的build.gradle里也是可以的,但是因為項目下的build.gradle里已經有buildscript {}、allprojects {repositories{} },就配置在這里了。

然后有兩種配置方式:

第一種

只有一個主Module app的情況下,配置app的build.gradle:

apply plugin: 'com.android.application'apply plugin: 'kotlin-android'apply plugin: 'kotlin-android-extensions'apply plugin: 'org.greenrobot.greendao'android {  compileSdkVersion rootProject.ext.compileSdkVersion  buildToolsVersion rootProject.ext.buildToolsVersion  defaultConfig {    applicationId "填入自己的applicationId"    minSdkVersion rootProject.ext.minSdkVersion    targetSdkVersion rootProject.ext.targetSdkVersion    versionCode 1    versionName "1.0"    //Lambda配置//    jackOptions.enabled = true//    android.compileOptions.sourceCompatibility 1.8    buildConfigField "boolean", "LOG", "true"// 顯示Log    testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"    //支持矢量圖    vectorDrawables.useSupportLibrary = true    ndk {      //選擇要添加的對應cpu類型的.so庫。      abiFilters 'armeabi', 'armeabi-v7a', 'arm64-v8a', 'x86', 'x86_64', 'mips', 'mips64'    }  }  buildTypes {    release {      minifyEnabled false      buildConfigField "boolean", "LOG", "false"// 顯示Log      proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'    }  }  //Lambda配置  compileOptions {    sourceCompatibility JavaVersion.VERSION_1_8    targetCompatibility JavaVersion.VERSION_1_8  }  dataBinding {    enabled true  }  greendao {    schemaVersion 1//數據庫版本號    daoPackage 'com.test.qby.newtestapplication.greendao'//設置DaoMaster、DaoSession、Dao包名    targetGenDir 'src/main/java'//設置DaoMaster、DaoSession、Dao目錄    //targetGenDirTest:設置生成單元測試目錄    //generateTests:設置自動生成單元測試用例  }  lintOptions {    abortOnError true  }}dependencies {  implementation fileTree(include: ['*.jar'], dir: 'libs')  implementation rootProject.ext.kotlinVersion  implementation rootProject.ext.appcompatV7  implementation rootProject.ext.constraintLayout  compile rootProject.ext.appcompatDesign  testImplementation 'junit:junit:4.12'  androidTestImplementation 'com.android.support.test:runner:1.0.1'  androidTestImplementation 'com.android.support.test.espresso:espresso-core:3.0.1'  compile 'jp.wasabeef:glide-transformations:3.0.1'  // If you want to use the GPU Filters  compile 'jp.co.cyberagent.android.gpuimage:gpuimage-library:1.4.1'  //騰訊bugly  compile 'com.tencent.bugly:crashreport:latest.release'  compile 'com.tencent.bugly:nativecrashreport:latest.release'  //retrofit  compile 'com.squareup.retrofit2:retrofit:2.3.0'  compile 'com.squareup.retrofit2:converter-gson:2.3.0'  compile 'com.squareup.retrofit2:adapter-rxjava2:2.3.0'  compile 'com.squareup.okhttp3:logging-interceptor:3.9.0'  //rxJava  compile 'io.reactivex.rxjava2:rxandroid:2.0.1'  // Because RxAndroid releases are few and far between, it is recommended you also  // explicitly depend on RxJava's latest version for bug fixes and new features.  compile 'io.reactivex.rxjava2:rxjava:2.1.8'  //greenDao  compile 'org.greenrobot:greendao:3.2.0'  //換膚功能  compile 'com.zhy:changeskin:4.0.2'  //AOP面向切面編程,加入這行就不用在libs下引入jar包了,不然要寫成compile file(libs/aspectjrt.jar)  compile 'org.aspectj:aspectjrt:1.8.13'}/*//在項目下配置了,此處就不需要了buildscript {  repositories {    mavenCentral()  }  dependencies {    classpath 'org.aspectj:aspectjtools:1.8.13'    classpath 'org.aspectj:aspectjweaver:1.8.13'  }}repositories {  mavenCentral()}*/import org.aspectj.bridge.IMessageimport org.aspectj.bridge.MessageHandlerimport org.aspectj.tools.ajc.Mainfinal def log = project.loggerfinal def variants = project.android.applicationVariantsvariants.all { variant ->  if (!variant.buildType.isDebuggable()) {    log.debug("Skipping non-debuggable build type '${variant.buildType.name}'.")    return  }  JavaCompile javaCompile = variant.javaCompile  javaCompile.doLast {    String[] args = ["-showWeaveInfo",             "-1.5",             "-inpath", javaCompile.destinationDir.toString(),             "-aspectpath", javaCompile.classpath.asPath,             "-d", javaCompile.destinationDir.toString(),             "-classpath", javaCompile.classpath.asPath,             "-bootclasspath", project.android.bootClasspath.join(File.pathSeparator)]    log.debug "ajc args: " + Arrays.toString(args)    MessageHandler handler = new MessageHandler(true)    new Main().run(args, handler)    for (IMessage message : handler.getMessages(null, true)) {      switch (message.getKind()) {        case IMessage.ABORT:        case IMessage.ERROR:        case IMessage.FAIL:          log.error message.message, message.thrown          break        case IMessage.WARNING:          log.warn message.message, message.thrown          break        case IMessage.INFO:          log.info message.message, message.thrown          break        case IMessage.DEBUG:          log.debug message.message, message.thrown          break      }    }  }}

這一個gradle主要的東西就是這些:

//AOP面向切面編程,加入這行就不用在libs下引入jar包了,不然要寫成compile file(libs/aspectjrt.jar)compile 'org.aspectj:aspectjrt:1.8.13'import org.aspectj.bridge.IMessageimport org.aspectj.bridge.MessageHandlerimport org.aspectj.tools.ajc.Mainfinal def log = project.loggerfinal def variants = project.android.applicationVariantsvariants.all { variant ->  if (!variant.buildType.isDebuggable()) {    log.debug("Skipping non-debuggable build type '${variant.buildType.name}'.")    return  }  JavaCompile javaCompile = variant.javaCompile  javaCompile.doLast {    String[] args = ["-showWeaveInfo",             "-1.5",             "-inpath", javaCompile.destinationDir.toString(),             "-aspectpath", javaCompile.classpath.asPath,             "-d", javaCompile.destinationDir.toString(),             "-classpath", javaCompile.classpath.asPath,             "-bootclasspath", project.android.bootClasspath.join(File.pathSeparator)]    log.debug "ajc args: " + Arrays.toString(args)    MessageHandler handler = new MessageHandler(true)    new Main().run(args, handler)    for (IMessage message : handler.getMessages(null, true)) {      switch (message.getKind()) {        case IMessage.ABORT:        case IMessage.ERROR:        case IMessage.FAIL:          log.error message.message, message.thrown          break        case IMessage.WARNING:          log.warn message.message, message.thrown          break        case IMessage.INFO:          log.info message.message, message.thrown          break        case IMessage.DEBUG:          log.debug message.message, message.thrown          break      }    }  }}

下面那一堆是用命令在編譯最后做一些關聯的,具體的我也不懂,只管加上好了。

第二種

有多個module都需要用到aspectj,特別是組件開發的情況下,不可能每個module都配置一下,所以就需要新建一個aspectj的module作為項目的library。

app下build.gradle需要修改:

//AOP面向切面編程,加入這行就不用在libs下引入jar包了,不然要寫成compile file(libs/aspectjrt.jar)compile 'org.aspectj:aspectjrt:1.8.13'

去掉,改為

implementation project(':aspectjlib')

不過上面這句在你添加module依賴的時候會自動生成。

新建library的build.gradle配置如下:

apply plugin: 'com.android.library'android {  compileSdkVersion rootProject.ext.compileSdkVersion  buildToolsVersion rootProject.ext.buildToolsVersion  defaultConfig {    minSdkVersion rootProject.ext.minSdkVersion    targetSdkVersion rootProject.ext.targetSdkVersion    versionCode 1    versionName "1.0"    testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"  }  buildTypes {    release {      minifyEnabled false      proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'    }  }}dependencies {  implementation fileTree(dir: 'libs', include: ['*.jar'])  implementation rootProject.ext.appcompatV7  testImplementation 'junit:junit:4.12'  androidTestImplementation 'com.android.support.test:runner:1.0.1'  androidTestImplementation 'com.android.support.test.espresso:espresso-core:3.0.1'  //AOP  compile 'org.aspectj:aspectjrt:1.8.13'}import org.aspectj.bridge.IMessageimport org.aspectj.bridge.MessageHandlerimport org.aspectj.tools.ajc.Mainandroid.libraryVariants.all { variant ->  JavaCompile javaCompile = variant.javaCompile  javaCompile.doLast {    String[] args = ["-showWeaveInfo",             "-1.5",             "-inpath", javaCompile.destinationDir.toString(),             "-aspectpath", javaCompile.classpath.asPath,             "-d", javaCompile.destinationDir.toString(),             "-classpath", javaCompile.classpath.asPath,             "-bootclasspath", android.bootClasspath.join(        File.pathSeparator)]    MessageHandler handler = new MessageHandler(true)    new Main().run(args, handler)    def log = project.logger    for (IMessage message : handler.getMessages(null, true)) {      switch (message.getKind()) {        case IMessage.ABORT:        case IMessage.ERROR:        case IMessage.FAIL:          log.error message.message, message.thrown          break        case IMessage.WARNING:        case IMessage.INFO:          log.info message.message, message.thrown          break        case IMessage.DEBUG:          log.debug message.message, message.thrown          break      }    }  }}

注意:下面那一堆跟app的gradle中的稍微有點區別,一個是module,一個是library,gradle中的東西不一樣。

兩種配置方式基本就是這樣了,使用方法我也是剛了解一點,記錄一下簡單的計算性能的用法吧

自定義注解類:

package com.test.qby.aspectjlib.annotation;import java.lang.annotation.ElementType;import java.lang.annotation.Retention;import java.lang.annotation.RetentionPolicy;import java.lang.annotation.Target;/** * Created by qby on 2018/1/26 0026. * 自定義注解 */@Target(ElementType.METHOD)@Retention(RetentionPolicy.RUNTIME)public @interface IFirstAnnotation {  String value();}

@Target 注解目標,表示注解使用在什么地方,這里是METHOD方法;@Retention 保留策略,表示注解調用時機,這里RUNTIME運行時

切面類

import android.widget.Toast;import com.test.qby.aspectjlib.annotation.IFirstAnnotation;import com.test.qby.newtestapplication.app.MyApplication;import org.aspectj.lang.ProceedingJoinPoint;import org.aspectj.lang.annotation.Around;import org.aspectj.lang.annotation.Aspect;import org.aspectj.lang.annotation.Pointcut;import org.aspectj.lang.reflect.MethodSignature;import java.lang.reflect.Method;import java.lang.reflect.TypeVariable;import java.util.Locale;/** * Created by qby on 2018/1/26 0026. * 自定義注解行為 */@Aspectpublic class MethodBehaviorAspect {  private static final String TAG = "aspect_aby";  @Pointcut("execution(@com.test.qby.aspectjlib.annotation.IFirstAnnotation * *(..))")  public void firstMethodAnnotationBehavior() {  }  @Pointcut("execution(* com.test.qby.newtestapplication.ui.MainActivity.aspectClick(android.view.View))")  public void secondMethodAnnotationBehavior() {  }  @Around("firstMethodAnnotationBehavior()")  public Object wavePointcutAround(ProceedingJoinPoint joinPoint) throws Throwable {    MethodSignature methodSignature = (MethodSignature) joinPoint.getSignature();    // 類名    String className = methodSignature.getDeclaringType().getSimpleName();    // 方法名    String methodName = methodSignature.getName();    // 功能名    IFirstAnnotation behaviorTrace = methodSignature.getMethod()        .getAnnotation(IFirstAnnotation.class);    String value = behaviorTrace.value();//    String value = "點擊";    long start = System.currentTimeMillis();    Object result = joinPoint.proceed();    long duration = System.currentTimeMillis() - start;    Log.e(TAG, String.format("%s類中%s方法執行%s功能,耗時:%dms", className, methodName, value, duration));    Toast.makeText(MyApplication.getContext(), String.format(Locale.CHINESE, "%s類中%s方法執行%s功能,耗時:%dms", className, methodName, value, duration), Toast.LENGTH_SHORT).show();    return result;  }}

@Aspect指定切面類;@Pointcut切入點;@Around是切入方式Advice的一種,表示在切入點前后插入代碼,還有@Before、@After;Pointcut語法,execution,表示根據Advice在執行方法內部代碼前后插入代碼,call,表示根據Advice在調用方法前后插入代碼......

頁面調用

@IFirstAnnotation("測試Aspect")public void aspectClick(View view) {   try {     Thread.sleep(new Random().nextInt(1000));   } catch (InterruptedException e) {     e.printStackTrace();   } }

@IFirstAnnotation調用注解,()內部為在IFirstAnnotation中寫的value的值,去掉value()后此處去掉()

注意:在MethodBehaviorAspect 類中如果有用到Context,可直接使用joinPoint.getTarget()類型轉換成Context,這里是由于項目使用了databinding,部分getTarget()獲取到的值不能強轉為Context,所以這里用的MyApplication獲取的Context

這只是個人的初步嘗試,里面當然還有很多內容需要去學,剛看了CSDN上有人寫的幾篇關于AOP的內容,都挺詳細的,給出其中一個地址

以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支持VEVB武林網。


注:相關教程知識閱讀請移步到Android開發頻道。
發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 吕梁市| 北海市| 霞浦县| 安阳县| 黔江区| 东台市| 凤山县| 中阳县| 芜湖市| 巩留县| 大庆市| 昌平区| 元氏县| 海原县| 迭部县| 安康市| 大方县| 榕江县| 宜黄县| 汝城县| 灌云县| 类乌齐县| 鞍山市| 三明市| 肃南| 惠安县| 南部县| 布尔津县| 泸定县| 印江| 石泉县| 金阳县| 龙门县| 禹州市| 淮南市| 吴川市| 安西县| 柳林县| 墨江| 库尔勒市| 和龙市|