// It will rebuild router map every times when debuggable. if (ARouter.debuggable() || PackageUtils.isNewVersion(context)) { logger.info(TAG, "Run with debug mode or new install, rebuild router map."); // These class was generated by arouter-compiler. routerMap = ClassUtils.getFileNameByPackageName(mContext, ROUTE_ROOT_PAKCAGE); if (!routerMap.isEmpty()) { context.getSharedPreferences(AROUTER_SP_CACHE_KEY, Context.MODE_PRIVATE).edit().putStringSet(AROUTER_SP_KEY_MAP, routerMap).apply(); }
PackageUtils.updateVersion(context); // Save new version name when router map update finishes. } else { logger.info(TAG, "Load router map from cache."); routerMap = newHashSet<>(context.getSharedPreferences(AROUTER_SP_CACHE_KEY, Context.MODE_PRIVATE).getStringSet(AROUTER_SP_KEY_MAP, newHashSet<String>())); }
if (null != callback) { callback.onFound(postcard); }
if (!postcard.isGreenChannel()) { // It must be run in async thread, maybe interceptor cost too mush time made ANR. interceptorService.doInterceptions(postcard, newInterceptorCallback() { @Override publicvoidonContinue(Postcard postcard) { _navigation(context, postcard, requestCode, callback); }
if (null == routeMeta) { //如果没有获取到路由的缓存对象,那么获取缓存中在初始化的时候保存的 class 即 ARouter$$Group$$modulea Class<? extendsIRouteGroup> groupMeta = Warehouse.groupsIndex.get(postcard.getGroup()); // Load route meta. if (null == groupMeta) { thrownewNoRouteFoundException(TAG + "There is no route match the path [" + postcard.getPath() + "], in group [" + postcard.getGroup() + "]"); } else { // Load route and cache it into memory, then delete from metas. try { //...此处省略部分代码
UrirawUri= postcard.getUri(); if (null != rawUri) { // Try to set params into bundle. Map<String, String> resultMap = TextUtils.splitQueryParameters(rawUri); Map<String, Integer> paramsType = routeMeta.getParamsType();
if (MapUtils.isNotEmpty(paramsType)) { // Set value by its type, just for params which annotation by @Param for (Map.Entry<String, Integer> params : paramsType.entrySet()) { setValue(postcard, params.getValue(), params.getKey(), resultMap.get(params.getKey())); }
// Save params name which need auto inject. postcard.getExtras().putStringArray(ARouter.AUTO_INJECT, paramsType.keySet().toArray(newString[]{})); }
// Save raw uri postcard.withString(ARouter.RAW_URI, rawUri.toString()); }
//根据路由类型执行不同逻辑 switch (routeMeta.getType()) { case PROVIDER: // if the route is provider, should find its instance // Its provider, so it must implement IProvider //通过路由信息获取到 ModuleAProvider.class Class<? extendsIProvider> providerMeta = (Class<? extendsIProvider>) routeMeta.getDestination(); //第一次拿到的是 null IProviderinstance= Warehouse.providers.get(providerMeta); if (null == instance) { // There's no instance of this provider IProvider provider; try { //通过 ModuleAProvider.class 的构造器创建实例 provider = providerMeta.getConstructor().newInstance(); //调用 ModuleAProvider 实例的 init 方法 provider.init(mContext); //将 Provider 放入缓存中 Warehouse.providers.put(providerMeta, provider); instance = provider; } catch (Exception e) { thrownewHandlerException("Init provider failed! " + e.getMessage()); } } //将 ModuleAProvider 实例放入 postcard 路由信息中 postcard.setProvider(instance); postcard.greenChannel(); // Provider should skip all of interceptors break; case FRAGMENT: postcard.greenChannel(); // Fragment needn't interceptors default: break; } } }
// Set flags. intflags= postcard.getFlags(); if (-1 != flags) { intent.setFlags(flags); } elseif (!(currentContext instanceof Activity)) { // Non activity, need less one flag. intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); }
// Set Actions Stringaction= postcard.getAction(); if (!TextUtils.isEmpty(action)) { intent.setAction(action); }
// Navigation in main looper. runInMainThread(newRunnable() { @Override publicvoidrun() { startActivity(requestCode, currentContext, intent, postcard, callback); } });
break; case PROVIDER: return postcard.getProvider(); case BOARDCAST: case CONTENT_PROVIDER: case FRAGMENT: ClassfragmentMeta= postcard.getDestination(); try { Objectinstance= fragmentMeta.getConstructor().newInstance(); if (instance instanceof Fragment) { ((Fragment) instance).setArguments(postcard.getExtras()); } elseif (instance instanceof android.support.v4.app.Fragment) { ((android.support.v4.app.Fragment) instance).setArguments(postcard.getExtras()); }
return instance; } catch (Exception ex) { logger.error(Consts.TAG, "Fetch fragment instance error, " + TextUtils.formatStackTrace(ex.getStackTrace())); } case METHOD: case SERVICE: default: returnnull; }
returnnull; }
因为我们postcard.getType()是PROVIDER类型的,所有直接返回了我们上一步在postcard中塞入创建的ModuleAProvider实例,接着就可以调用其sayHello方法了。 不难发现,其实在ARouter中Group的划分是以路径中第一对“/”中的字串作为基准的,一开始会将根据不同Group生成的ARouter$$Group$$字串的 class 放入Warehouse中缓存,然后根据调用的 path 将不同Group的具体路径对应的具体路由加载进Warehouse,再获取对应的RouteMeta路由信息,重新组装到postcard中,最后调用_navigation根据postcard不同的类型执行相应的逻辑。还有一点非常明显,当我们调用ARouter的方法的时候最终都会交由_ARouter去执行,这里用到的是结构性设计模式中的外观模式。 大致分析就是如此了。