|
- /**
- * 扩大点扫描、注册
- */
- public class ExtPointBeanPostProcess implements BeanPostProcessor {
- @Override
- public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
- return bean;
- }
- /**
- * 辨認扩大点实例, 并完成扩大点注册
- * 1.扩大点必需实現IExtensionPoint接口
- * 2.强迫请求扩大点接口名必需以ExtPt末端
- */
- @Override
- public Object台中機車借款, postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
- if (bean instanceof IExtensionPoint) {
- IExtensionPoint extPoint = (IExtensionPoint) bean;
- ExtensionCoordinate coordinate = parseExtensionCoordinate(bean.getClass());
- IExtensionPoint oldValue = ExtensionManager.getInstance()
- .registerExtPoint(coordinate, extPoint);
- if (Objects.nonNull(oldValue)) {
- throw new MidFrameworkException("Duplicate registration for :" + coordinate);
- }
- }
- return bean;
- }
- private ExtensionCoordinate parseExtensionCoordinate(Class<?> targetBean) {
- // 扩大点接口
- Optional<Class> extPointClass = checkExtensionPoint(targetBean);
- if (!extPointClass.isPresent()) {
- throw new MidFrameworkException(
- String.format("The name of ExtensionPoint for %s must be end with %s", targetBean, IExtensionPoint.EXT_POINT_NAMING));
- }
- // 解析@Extension注解
- AnnotationAttributes attrs = AnnotatedElementUtils.getMergedAnnotationAttributes(targetBean, Extension.class);
- String bizCode = attrs.getString("bizCode");
- String name = attrs.getString("name");
- String description = attrs.getString("description");
- return ExtensionCoordinate.builder()
- .bizCode(bizCode)
- .extensionPoint(extPointClass.get().getName())
- .name(name)
- .description(description)
- .build();
- }
- private Optional<Class> checkExtensionPoint(Class<?> targetBean) {
- Class[] interfaces = targetBean.getInterfaces();
- if (interfaces == null || interfaces.length == 0) {
- throw new MidFrameworkException("No extension point interface for " + targetBean);
- }
- // 扩大点接口名必需以ExtPt末端
- return Arrays.stream(interfaces)
- .filter(ext -> ext.getSimpleName().endsWith(IExtensionPoint.EXT_POINT_NAMING))
- .findFirst();
- }
- }
複製代碼
颠末以上步调,體系已启動完成,而且所有的扩大点也都完成为了注册。剩下的就是怎样去挪用扩大点法子了!因为统一個扩大点的所有实例多是统一個名字,好比都叫
BuyExtPointImpl,明顯不克不及經由過程Spring的依靠注入来挪用。究竟上,扩大点实例的挪用,都是同一走扩大点履行器,其内部封装了扩大点查找逻辑和履行逻辑,代码注释應當写得比力清晰了。
- /**
- * 扩大点实例履行器: 封装扩大点查找计谋及法子挪用
- */
- public class ExtensionExecutor {
- private ExtensionExecutor() {
- throw new IllegalStateException("No instance");
- }
- /**
- * 有返回值
- *
- * @param targetClass 扩大点类名
- * @param bizId 营業身份
- * @param exeFunction 必要挪用的扩大点法子
- */
- public static <R, T> R execute(BizId bizId, Class<T> targetClass, Function<T, R> exeFunction) {
- T component = findComponent(bizId, targetClass);
- return exeFunction.apply(component);
- }
- /**
- * 無返回值
- *
- * @param targetClass 扩大点类名
- * @param bizId 营業身份
- * @param exeConsumer 必要挪用的扩大点法子
- */
- public static <T> void consume(BizId bizId, Class<T> targetClass, Consumer<T> exeConsumer) {
- T component = findComponent(bizId, targetClass);
- exeConsumer.accept(component);
- }
- /**
- * 切确查找扩大点: 先看是不是有营業实現的扩大点;若没有,再看是不是有平台默许实現
- */
- @SuppressWarnings("unchecked")
- private static <T> T findComponent(BizId bizId, Class<T> targetClass) {
- ExtensionCoordinate bizCoordinate = ExtensionCoordinate.of(bizId.getBizCode(), targetClass.getName());
- IExtensionPoint extension = ExtensionManager.getInstance().findExtPoint(bizCoordinate);
- if (Objects.isNull(extension)) {
- ExtensionCoordinate systemCoordinate = ExtensionCoordinate.of(IExtensionPoint.SYSTEM_BIZ_CODE,
- targetClass.getName());
- extension = ExtensionManager.getInstance().findExtPoint(systemCoordinate);
- }
- if (Objects.isNull(extension)) {
- throw new MidFrameworkException("Not found extension: " + bizCoordinate);
- }
- return (T) extension;
- }
- }
複製代碼
下面以一個单测为例演示扩大点的履行 ExtensionExecutor.execute()
- @Test
- public void testTaobaoExt() {
- BizId bizId = new BizId("com.taobao");
- int promotion = ExtensionExecutor.execute(bizId, PromotionCalcExtPoint.class,
- PromotionCalcExtPoint::calcPromotion);
- Assert.539版路單,assertEquals(promotion, 80);
- }
- @Test
- public void testTmallExt() {
- BizId bizId = new BizId("com.tmall");
- int promotion = ExtensionExecutor.exec君綺PTT,ute(隱形矯姿帶,bizId, PromotionCalcExtPoint.class,
- PromotionCalcExtPoint::calcPromotion);
- Assert.assertEquals(promotion, 90);
- }
複製代碼
上面2末節,已把扩大点注册和扩大点履行,触及到的数据模子、運行機制論述清晰了。這里再補一幅圖来個更直观感觉。 |
|