日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

android 短信 aapp,谈谈App的统一跳转和ARouter

發(fā)布時(shí)間:2023/12/10 编程问答 29 豆豆
生活随笔 收集整理的這篇文章主要介紹了 android 短信 aapp,谈谈App的统一跳转和ARouter 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

App中每次頁(yè)面跳轉(zhuǎn),都需要調(diào)用統(tǒng)一導(dǎo)航, 它用的非常頻繁, 有必要對(duì)它進(jìn)行一下梳理. 讓他能用起來簡(jiǎn)單方便, 同時(shí)能支持各種常用的跳轉(zhuǎn)業(yè)務(wù)場(chǎng)景.

一. Android跳轉(zhuǎn)遇到的問題

1.intent-filter跳轉(zhuǎn)不好管理

Intent intent = new Intent();

intent.setAction(Intent.ACTION_SENDTO);

intent.setData(Uri.parse("smsto:10086"));

context.startActivity(intent);

如果項(xiàng)目分多個(gè)Module, Activity需要在各自Module的AndroidManifest.xml中聲明,容易重復(fù),不好統(tǒng)一管理.

2.Activity class跳轉(zhuǎn)耦合性高

//通過設(shè)置目標(biāo)class跳轉(zhuǎn)

Intent intent = new Intent();

intent.setClass(context,TargetActivity.class);

context.startActivity(intent);

A如果要跳轉(zhuǎn)到TargetActivity, A要引用到TargetActivity. 造成:

如果項(xiàng)目多個(gè)Module開發(fā),底層module不能跳轉(zhuǎn)到高層Activity

如果TargetActivity類名變化, 對(duì)應(yīng)調(diào)用方都需要改動(dòng)

3. 混合開發(fā)時(shí),H5/Weex跳轉(zhuǎn)新界面不方便

內(nèi)置H5要跳轉(zhuǎn) Native頁(yè)面, 通過JsBidge把目標(biāo)信息傳過來.

兩種方式:

方式1: 直接提供目標(biāo)Activity的 Action 跳過去.

方式2: Native維護(hù)一個(gè)的Map, H5傳過來Activiy的"描述", Native在Map中查到后,進(jìn)行跳轉(zhuǎn).

方式1的問題:

一般H5會(huì)同時(shí)在"Android/ios"容器中, 所以最好的實(shí)踐是:H5做跳轉(zhuǎn)時(shí)不需要區(qū)分平臺(tái)和版本. 如果利用Action跳轉(zhuǎn),

1)Action命名要符合兩個(gè)平臺(tái)的規(guī)范

2)如果Native不支持目標(biāo)Action,還需要做跳轉(zhuǎn)失敗后處理.

方式2的問題:

1)維護(hù)的列表麻煩事,需要單獨(dú)角色管理.

2)同樣存的"Activity信息"也有問題1,2中提到的問題

都有的問題:

處理跳轉(zhuǎn)的Bridge類,可能拿不到context,這需要拿Application的Context,大家都判斷略嫌麻煩.

4.跳轉(zhuǎn)到"未知頁(yè)面"的統(tǒng)一處理

比如2.0版本新加了"消息"功能,App1.0版本沒有.

此時(shí)1.0版本的App中,"H5/push" 嘗試打開"消息"頁(yè)面, 肯定是不支持的. 這時(shí)候有幾種策略:

H5/Push能判斷Native支持頁(yè)面的能力,如果不支持,就不調(diào)用

Native收到調(diào)用未知頁(yè)面, 不做任何動(dòng)作.

Native收到調(diào)用未知頁(yè)面, 提示這是新版功能,建議更新版本.

5. 業(yè)務(wù)降級(jí)/重定向

比如A/B測(cè)試:

Native可以根據(jù)配置, 跳轉(zhuǎn)不同的實(shí)現(xiàn)頁(yè)面

業(yè)務(wù)降級(jí):

某個(gè)業(yè)務(wù)本來Native實(shí)現(xiàn), 降級(jí)為H5實(shí)現(xiàn), 這時(shí)候跳轉(zhuǎn)時(shí)切換到H5頁(yè)面.

6.統(tǒng)一加參

跳轉(zhuǎn)到目標(biāo)頁(yè)面前,能統(tǒng)一加參數(shù).

實(shí)現(xiàn)比如打點(diǎn), 添加通用參數(shù)操作.

7.外部調(diào)用的統(tǒng)一入口

考慮這種業(yè)務(wù)場(chǎng)景: App有 A,B,C三個(gè)頁(yè)面, 提供給外部調(diào)用.

這時(shí)候一般兩種實(shí)現(xiàn)方式:

方式1: A,B,C的Activity 在AndroidManifest.xml中export=true,并且設(shè)置 intent-filter

方式2: App設(shè)置一個(gè)統(tǒng)一的Router-Activity, 外部跳轉(zhuǎn)到A,B,C 都統(tǒng)一先統(tǒng)一到Router-Activity, 他在拉起A,B,C

方式1分析:

除非真的提供通用的功能(拍照/圖片處理/..)給外部調(diào)用, 否則export一個(gè)Activity是不必要也不安全的. 為了安全,App不會(huì)export大量的Activity. 這意味著通過這種機(jī)制, 外部能調(diào)用內(nèi)部的功能較少.

方式2分析:

優(yōu)點(diǎn):

只暴露了一個(gè)Router-Activity. 安全和好管理.

Router-Activity里面可以做一些調(diào)用者的安全校驗(yàn), 如果校驗(yàn)通過可以運(yùn)行跳轉(zhuǎn)App的全部頁(yè)面. 這樣給能外部調(diào)用app更多頁(yè)面的機(jī)會(huì), 也兼顧了安全.

缺點(diǎn):

外部跳轉(zhuǎn)需要一個(gè)Activity中轉(zhuǎn)一下,直觀上感覺效率低一些. 但是實(shí)際感覺基本沒有影響.

二. 明確需求

根據(jù)問題和業(yè)務(wù)場(chǎng)景, 我們的"統(tǒng)一跳轉(zhuǎn)"的需求也基本明確:

"聲明/使用" 簡(jiǎn)單.

適用多module開發(fā),避免直接依賴.

統(tǒng)一協(xié)議, 適用"H5/Weex/Native" 跳轉(zhuǎn) "Native", 對(duì)"Android/ios"兩個(gè)平臺(tái)協(xié)議應(yīng)該是一樣的.

有統(tǒng)一的外部調(diào)用入口

能對(duì)"不支持"的跳轉(zhuǎn)統(tǒng)一處理

支持跳轉(zhuǎn)前預(yù)處理

支持重定向

三.解決方案ARouter

ARouter

ARouter-github 很好的解決了上述問題.

下面是他的對(duì)應(yīng)的方案.

1.使用簡(jiǎn)單:

每個(gè)Activity在類中自聲明,"代碼-路徑"對(duì)應(yīng)一目了然

@Route(path = "/test/activity")

public class YourActivity extend Activity {

...

}

跳轉(zhuǎn)新頁(yè)面簡(jiǎn)單,不需要知道目標(biāo)ActivityContext,intent-filter,目標(biāo)的Activity

ARouter.getInstance().build(path).with(bundle).navigation();

2.頁(yè)面利于統(tǒng)一管理

所有頁(yè)面可以統(tǒng)一定義. 一目了然

String PAGE_MAIN = "/navigateTo/main";

String PAGE_H5 = "/navigateTo/h5";

String PAGE_WEEX = "/navigateTo/weex";

...

3.便于設(shè)置統(tǒng)一Activity承載外部跳轉(zhuǎn)

public class SchameFilterActivity extends Activity {

@Override

protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

//安全/版本校驗(yàn)

....

Uri uri = getIntent().getData();

ARouter.getInstance().build(uri).navigation();

finish();

}

}

4.處理"未知頁(yè)面"的跳轉(zhuǎn)結(jié)果

ARouter.getInstance().build("/test/1").navigation(this, new NavigationCallback() {

@Override

public void onFound(Postcard postcard) {

...

}

@Override

public void onLost(Postcard postcard) {

//可以處理,提示升級(jí)版本之類

}

});

5. 自定義全局降級(jí)策略

// 實(shí)現(xiàn)DegradeService接口,并加上一個(gè)Path內(nèi)容任意的注解即可

@Route(path = "/xxx/xxx")

public class DegradeServiceImpl implements DegradeService {

@Override

public void onLost(Context context, Postcard postcard) {

// do something.

}

@Override

public void init(Context context) {

}

}

6. 重寫跳轉(zhuǎn)URL實(shí)現(xiàn)重定向

// 實(shí)現(xiàn)PathReplaceService接口,并加上一個(gè)Path內(nèi)容任意的注解即可

@Route(path = "/xxx/xxx") // 必須標(biāo)明注解

public class PathReplaceServiceImpl implements PathReplaceService {

/**

* For normal path.

*

* @param path raw path

*/

String forString(String path) {

return path; // 按照一定的規(guī)則處理之后返回處理后的結(jié)果

}

/**

* For uri type.

*

* @param uri raw uri

*/

Uri forUri(Uri uri) {

return url; // 按照一定的規(guī)則處理之后返回處理后的結(jié)果

}

}

技術(shù)分析

1.建立 Url-Activity 的對(duì)應(yīng)關(guān)系

ARouter最后是通過下面方式跳轉(zhuǎn)的.

//_ARouter.java

Intent intent = new Intent(currentContext,postcard.getDestination());

intent.putExtras(postcard.getExtras());

所以要AROUTER需要維護(hù)一個(gè) Path和Activity class的對(duì)應(yīng)關(guān)系.

他利用

javapoet在編譯時(shí)候生成類信息

初始化時(shí),收集主創(chuàng)Path/Activity信息. 所有信息存在WareHouse中.

screenshot.png

2. 跳轉(zhuǎn)流程

screenshot.png

其他技術(shù)

1. 屬性設(shè)置在gradle.properties中

BUILDTOOLS_VERSION=25.0.0

使用:

compile "com.android.support:support-v4:${SUPPORT_LIB_VERSION}"

buildToolsVersion BUILDTOOLS_VERSION

2.TreeMap

HashMap通過hashcode對(duì)其內(nèi)容進(jìn)行快速查找,而 TreeMap中所有的元素都保持著某種固定的順序,如果你需要得到一個(gè)有序的結(jié)果你就應(yīng)該使用TreeMap(HashMap中元素的排列順序是不固定的)

3.Instrumentation的使用

你可以將Instrumentation理解為一種沒有圖形界面

的,具有啟動(dòng)能力的,用于監(jiān)控其他類(用Target

Package聲明)的工具類。任何想成為Instrumentation的類必須繼承android.app.Instrumentation。

下面是這個(gè)類的解釋:

“Base class for implementing application instrumentation code. When running with instrumentation turned on, this class will be instantiated for you before any of the application code, allowing you to monitor all of the interaction the system has with the application. An Instrumentation implementation is described to the system through an AndroidManifest.xml's tag.“

4.volatile

volatile重要工作是避免線程臟讀:當(dāng)線程對(duì)volatile變量進(jìn)行讀操作時(shí),會(huì)先將2. 自己工作內(nèi)存中的變量置為無(wú)效,之后再通過主內(nèi)存拷貝新值到工作內(nèi)存中使用。

volatile解決的是變量在多個(gè)線程之間的可見性,但不能完全保證數(shù)據(jù)的原子性。

現(xiàn)在JVM經(jīng)過優(yōu)化,已不會(huì)出現(xiàn)liveness failure 。所以沒事別用volatile。

5. CountDownLatch

CountDownLatch的一個(gè)非常典型的應(yīng)用場(chǎng)景是:有一個(gè)任務(wù)想要往下執(zhí)行,但必須要等到其他的任務(wù)執(zhí)行完畢后才可以繼續(xù)往下執(zhí)行。假如我們這個(gè)想要繼續(xù)往下執(zhí)行的任務(wù)調(diào)用一個(gè)CountDownLatch對(duì)象的await()方法,其他的任務(wù)執(zhí)行完自己的任務(wù)后調(diào)用同一個(gè)CountDownLatch對(duì)象上的countDown()方法,這個(gè)調(diào)用await()方法的任務(wù)將一直阻塞等待,直到這個(gè)CountDownLatch對(duì)象的計(jì)數(shù)值減到0為止。

6.獲取CPU個(gè)數(shù)

CPU_COUNT = Runtime.getRuntime().availableProcessors()

7.捕捉線程異常

// 捕獲多線程處理中的異常

thread.setUncaughtExceptionHandler(new Thread.UncaughtExceptionHandler() {

@Override

public void uncaughtException(Thread thread, Throwable ex) {

ARouter.logger.info(Consts.TAG, "Running task appeared exception! Thread [" + thread.getName() + "], because [" + ex.getMessage() + "]");

}

});

build classpath 'com.neenbedankt.gradle.plugins:android-apt:1.4'

使用 annotationProcessor

dependencies {

annotationProcessor project(':arouter-compiler')

}

9.Activity啟動(dòng)

int flags = postcard.getFlags();

if (-1 != flags) {

intent.setFlags(flags);

} else if (!(currentContext instanceof Activity)) {

// Non activity, need less one flag.

intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

}

10. 訪問者模式

//設(shè)置WareHouse

public interface IRouteGroup {

/**

* Fill the atlas with routes in group.

*/

void loadInto(Map atlas);

}

iGroupInstance.loadInto(Warehouse.routes);

創(chuàng)作挑戰(zhàn)賽新人創(chuàng)作獎(jiǎng)勵(lì)來咯,堅(jiān)持創(chuàng)作打卡瓜分現(xiàn)金大獎(jiǎng)

總結(jié)

以上是生活随笔為你收集整理的android 短信 aapp,谈谈App的统一跳转和ARouter的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。