架构系列——java动态代理中的InvocationHandler和Proxy

简介: 架构系列——java动态代理中的InvocationHandler和Proxy

前言

先赞后看,此生必赚!

Java中动态代理的实现,主要是InvocationHandler和Proxy的使用。

可以通过以下步骤实现一个动态代理:

一、创建正常的接口以及实现类

1. 接口:

public interface People {
  public void working();
}

2. 实现类:

public class Student implements People {
  @Override
  public void work() {
    System.out.println("正在学习...");
  }
}

二、创建一个PeopleHandler实现InvocationHandler

public class PeopleHandler implements InvocationHandler {
  private Object obj;
  public PeopleHandler(Object obj) {
    this.obj = obj;
  }
  public Object getProxy(Object obj) {
    return Proxy.newProxyInstance(obj.getClass().getClassLoader(), obj.getClass().getInterfaces(), this);
  }
  @Override
  public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
    System.out.println("before invoke...");
    Object result = method.invoke(obj, args);
    System.out.println("after invoke...");
    return result;
  }
}u

解读:

PeopleHandler(Object obj):通过被代理对象创建handler;


getProxy(Object obj):通过被代理对象创建代理;


invoke(Object proxy, Method method, Object[] args):代理不直接调用invoke,而是使用正常的方法时都会走invoke方法;

三、调用方法

可以使用两种方式调用方法:

1. 直接调用

不使用代理类直接调用,直接实现业务逻辑

2. 使用代理类调用

使用代理类调用,间接实现业务逻辑

public class TestProxy {
  public static void main(String[] args) {
    //1.直接调用
    System.out.println("直接调用:");
    People people = new Student();
    people.work();
    //2.通过代理调用
    System.out.println("\n通过代理调用:");
    PeopleHandler handler = new PeopleHandler(people);
    People proxy = (People) handler.getProxy(people);
    proxy.work();
  }
}

结果:

直接调用:
正在学习...
通过代理调用:
before invoke...
正在学习...
after invoke...

四、总结

1. 使用代理的好处

从上面的案例可以看出,两者都可以实现正常的业务逻辑,那为啥要多此一举地使用代理类呢?

1.1 降低耦合度

正常逻辑work()与日志的关系没那么强烈,可以对业务逻辑的各个部分进行隔离。


1.2 提高可重用性

如果不使用代理,需要每一次在调用work()前后都要写日志,这样的话,代码的可重用性为0!


使用代理之后,只需要在handler的invoke()方法中写一次即可,重用性明显提高!


2. 使用场景

除了上面案例中的日志,还有性能统计,安全控制,事务处理,异常处理等等。


安全控制举例:


校验用户权限,每一个菜单请求,都要判断一下请求的用户是否有该菜单权限。菜单多了,代码冗余,且容易遗漏。


通过动态代理就可以实现为:每一个用户,每一个菜单的请求,都经过代理(proxy),由他判断是否有权限,调用者只需要调用,实现自己的逻辑,不关心权限问题。


相关文章
|
1月前
|
消息中间件 Java Kafka
Java 事件驱动架构设计实战与 Kafka 生态系统组件实操全流程指南
本指南详解Java事件驱动架构与Kafka生态实操,涵盖环境搭建、事件模型定义、生产者与消费者实现、事件测试及高级特性,助你快速构建高可扩展分布式系统。
111 7
|
4月前
|
负载均衡 算法 关系型数据库
大数据大厂之MySQL数据库课程设计:揭秘MySQL集群架构负载均衡核心算法:从理论到Java代码实战,让你的数据库性能飙升!
本文聚焦 MySQL 集群架构中的负载均衡算法,阐述其重要性。详细介绍轮询、加权轮询、最少连接、加权最少连接、随机、源地址哈希等常用算法,分析各自优缺点及适用场景。并提供 Java 语言代码实现示例,助力直观理解。文章结构清晰,语言通俗易懂,对理解和应用负载均衡算法具有实用价值和参考价值。
大数据大厂之MySQL数据库课程设计:揭秘MySQL集群架构负载均衡核心算法:从理论到Java代码实战,让你的数据库性能飙升!
|
5月前
|
人工智能 安全 Java
智慧工地源码,Java语言开发,微服务架构,支持分布式和集群部署,多端覆盖
智慧工地是“互联网+建筑工地”的创新模式,基于物联网、移动互联网、BIM、大数据、人工智能等技术,实现对施工现场人员、设备、材料、安全等环节的智能化管理。其解决方案涵盖数据大屏、移动APP和PC管理端,采用高性能Java微服务架构,支持分布式与集群部署,结合Redis、消息队列等技术确保系统稳定高效。通过大数据驱动决策、物联网实时监测预警及AI智能视频监控,消除数据孤岛,提升项目可控性与安全性。智慧工地提供专家级远程管理服务,助力施工质量和安全管理升级,同时依托可扩展平台、多端应用和丰富设备接口,满足多样化需求,推动建筑行业数字化转型。
175 5
|
2月前
|
缓存 Java 数据库
Java 项目分层架构实操指南及长尾关键词优化方案
本指南详解基于Spring Boot与Spring Cloud的Java微服务分层架构,以用户管理系统为例,涵盖技术选型、核心代码实现、服务治理及部署实践,助力掌握现代化Java企业级开发方案。
121 2
|
3月前
|
算法 架构师 Java
Java 开发岗及 java 架构师百度校招历年经典面试题汇总
以下是百度校招Java岗位面试题精选摘要(150字): Java开发岗重点关注集合类、并发和系统设计。HashMap线程安全可通过Collections.synchronizedMap()或ConcurrentHashMap实现,后者采用分段锁提升并发性能。负载均衡算法包括轮询、加权轮询和最少连接数,一致性哈希可均匀分布请求。Redis持久化有RDB(快照恢复快)和AOF(日志更安全)两种方式。架构师岗涉及JMM内存模型、happens-before原则和无锁数据结构(基于CAS)。
80 5
|
2月前
|
缓存 Cloud Native Java
Java 面试微服务架构与云原生技术实操内容及核心考点梳理 Java 面试
本内容涵盖Java面试核心技术实操,包括微服务架构(Spring Cloud Alibaba)、响应式编程(WebFlux)、容器化(Docker+K8s)、函数式编程、多级缓存、分库分表、链路追踪(Skywalking)等大厂高频考点,助你系统提升面试能力。
105 0
|
4月前
|
存储 监控 算法
Java程序员必学:JVM架构完全解读
Java 虚拟机(JVM)是 Java 编程的核心,深入理解其架构对开发者意义重大。本文详细解读 JVM 架构,涵盖类加载器子系统、运行时数据区等核心组件,剖析类加载机制,包括加载阶段、双亲委派模型等内容。阐述内存管理原理,介绍垃圾回收算法与常见回收器,并结合案例讲解调优策略。还分享 JVM 性能瓶颈识别与调优方法,分析 Java 语言特性对性能的影响,给出数据结构选择、I/O 操作及并发同步处理的优化技巧,同时探讨 JVM 安全模型与错误处理机制,助力开发者提升编程能力与程序性能。
Java程序员必学:JVM架构完全解读
|
6月前
|
机器学习/深度学习 数据采集 Java
基于DeepSeek与RAG的智能天气预报系统架构设计与Java实现
基于DeepSeek与RAG的智能天气预报系统架构设计与Java实现
286 3

热门文章

最新文章