从零并发框架(三)异步转同步注解+字节码增强代理实现( 二 )
这里就有我们开头定义的注解信息 , 还有一些字节码增强相关的信息 , 比如方法 , 参数等等 。
同步实现核心代码同步实现的核心代码如下:
package com.github.houbb.sync.core.core;import com.github.houbb.heaven.util.lang.ObjectUtil;import com.github.houbb.heaven.util.lang.reflect.ClassUtil;import com.github.houbb.sync.api.annotation.Sync;import com.github.houbb.sync.api.annotation.SyncCallback;import com.github.houbb.sync.api.api.*;import com.github.houbb.sync.api.exception.SyncRuntimeException;import com.github.houbb.sync.core.support.context.SyncLockContext;import com.github.houbb.sync.core.support.context.SyncUnLockContext;import com.github.houbb.sync.core.support.lock.Locks;import java.lang.reflect.Method;/** * @author binbin.hou * @since 0.0.1 */public class SimpleSync implements ISync {@Overridepublic Object sync(ISyncContext context) throws Throwable {//1. 判断是 sync 还是 callbackSync sync = context.sync();if(ObjectUtil.isNotNull(sync)) {ISyncLock syncLock = Locks.getLock(sync.lock());ISyncLockContext lockContext = SyncLockContext.newInstance().timeout(sync.timeout()).timeUnit(sync.timeUnit());// 方法执行完成之前加锁syncLock.lock(lockContext);return context.process();}SyncCallback callback = context.callback();if(ObjectUtil.isNotNull(callback)) {Sync matchSync = getMatchSync(context.method(), callback);ISyncLock syncLock = Locks.getLock(matchSync.lock());ISyncUnlockContext unlockContext = SyncUnLockContext.newInstance().timeout(matchSync.timeout()).timeUnit(matchSync.timeUnit());Object result = context.process();// 方法执行完成之后解锁syncLock.unlock(unlockContext);return result;}return context.process();}}
根据上下文中的注解信息 , 判断是执行加锁 , 还是解锁 。
那加/解锁与方法执行的先后顺序呢?
机智如你不妨花一分钟想一想这个简单的问题 。
60
59
...
01
注意加锁解锁的顺序 , 方法执行完成之前加锁 , 方法执行完成之后解锁 。
如果是解锁 , 则需要获取对应的 @Sync 注解 。 方法试下如下:
获取匹配的回调信息/** * 获取匹配的回调信息 * @param method 回调方法 * @param callback 回调方法注解信息 * @return 结果 * @since 0.0.1 */private Sync getMatchSync(final Method method,final SyncCallback callback) {String value = http://kandian.youth.cn/index/callback.value();Class> clazz = method.getDeclaringClass();Method syncMethod = ClassUtil.getMethod(clazz, value);Sync sync = syncMethod.getAnnotation(Sync.class);if(ObjectUtil.isNull(sync)) {throw new SyncRuntimeException(value + " 方法未指定 @Sync 注解信息!");}return sync;}
这里会根据 @SyncCallback 注解中指定的方法名称 , 遍历当前类的方法 , 返回匹配的信息 。
如果方法不存在 , 或者方法没有指定 @Sync 都会进行报错 。
字节码增强字节码增强的方式万事俱备只欠东风 。
下面我们只需要使用字节码增强技术 , 就可以把整个调用链路串联起来 。
这里我们使用代理模式 , 对所有的方法进行增强 。
主要有三类:
(1)不需要代理的
(2)有接口的方法 , 可以通过 jdk 动态代理
(3)没有接口的方法 , 我们通过 cglib 进行代码增强 。
增强的方法我们为 Sync 同步实现添加了一个引导类 , 便于代理中调用 , 实际上就是调用上面的方法 , 实现也非常简单:
- 图解|什么是高并发利器NoSQL
- 怎么理解分布式、高并发、多线程
- 写给大忙人看的,MyBatis日志如何做到兼容常用的日志框架
- 为什么 Django 框架持续统治着 Python 开发?
- 点云分类的自动放大框架 PointAugment
- 深入理解Logger日志——框架绑定原理
- 理解真实世界中 Go 的并发 BUG
- Go 中的 Goroutine 和其他并发处理方案的对比
- 迅易科技|| 拥抱“云”,更懂“云”,企业云采用框架落地实践
- 安卓|打破传统安卓系统框架!OriginOS的UI设计果然不俗