插件结构如图:

注册模块定义了三个:用于实体与表映射的注解,用于属性到表字段的映射,用于映射时过滤掉的注解.

1.用于实体与表映射的注解

package com.dobby.plugins.annotation;

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target; /**
* User: 苏若年
* Date: 14-10-9
* Time: 下午21:12
* Description:
*/ @Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
public @interface GeneratorTable { //标注映射时的表名
public String name() default ""; }

2.用于属性与字段映射的注解

package com.dobby.plugins.annotation;

import java.lang.annotation.*;

/**
* User: 苏若年
* Date: 14-10-9
* Time: 下午21:31
* Description:
*/
@Target({ElementType.METHOD,ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Inherited
@Documented
public @interface GeneratorField { /**
* 是否为主键
* @return
*/
boolean primaryKey() default false; /**
* 映射的字段名
* @return
*/
public String name() default "";
}

3.用于废弃字段过滤的注解

package com.dobby.plugins.annotation;

import java.lang.annotation.*;

/**
* User: 苏若年
* Date: 14-10-9
* Time: 下午21:15
* Description:
*/
@Target({ElementType.METHOD,ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Inherited
@Documented
public @interface AbolishedField {
//标注映射时排除的字段
}

注解定义完成后,我们需要在扫描到的实体中根据注解映射规则进行扫描时自动封装

自动封装的核心业务逻辑如下

    /**
* 根据对象构造,表映射
* @param object
* 实体对象
* @return
* 实体对象到字段表的映射,基于注解处理
*/
public static EntityTable constructEntityTableWithObject(Object object){
EntityTable entityTable = null;
try{
if(null == object){return null;} ConcurrentMap<String,String> entityToTable = new ConcurrentHashMap<String, String>();
boolean isGeneratorTable = object.getClass().isAnnotationPresent(GeneratorTable.class);
System.out.println(object.getClass().getSimpleName());
if(isGeneratorTable){
GeneratorTable generatorTable = object.getClass().getAnnotation(GeneratorTable.class);
if(StringUtils.isBlank(generatorTable.name())){
entityToTable.put(object.getClass().getSimpleName(),firstLower(object.getClass().getSimpleName()));
}else{
entityToTable.put(object.getClass().getSimpleName(),generatorTable.name());
}
}else{
entityToTable.put(object.getClass().getSimpleName(),firstLower(object.getClass().getSimpleName()));
}
Field[] fields = object.getClass().getDeclaredFields();
if(null != fields){
entityTable = new EntityTable();
//主键组
ConcurrentMap<String,String> propertyToKey = new ConcurrentHashMap<String,String>();
//字段组
ConcurrentMap<String,String> propertyToColumn = new ConcurrentHashMap<String, String>();
//主键到集合类型映射
ConcurrentMap<String,Object> propertyPKeyType = new ConcurrentHashMap<String,Object>(); for (int i = 0; i < fields.length; i++) {
//判断是否剔除
boolean isAbolishedField = fields[i].isAnnotationPresent(AbolishedField.class);
if(isAbolishedField){
//跳过该字段的提取
continue;
}
//判断是否是主键
boolean isGeneratorField = fields[i].isAnnotationPresent(GeneratorField.class);
if(isGeneratorField){
// 取注解中的文字说明
GeneratorField generatorField = fields[i].getAnnotation(GeneratorField.class);
boolean primaryKey = generatorField.primaryKey();
if(primaryKey){
//添加到主键集合
propertyPKeyType.put(fields[i].getName(),fields[i].getType().getName());
propertyToKey.put(fields[i].getName(),generatorField.name());
}else{
if(StringUtils.isBlank(generatorField.name())){
propertyToColumn.put(fields[i].getName(),fields[i].getName());
}else{
propertyToColumn.put(fields[i].getName(),generatorField.name());
}
}
continue;
}
propertyToColumn.put(fields[i].getName(), fields[i].getName());
}
entityTable.setPropertyPKeyType(propertyPKeyType);
entityTable.setPropertyToPKey(propertyToKey);
entityTable.setPropertyToColumn(propertyToColumn);
}
entityTable.setEntityToTable(entityToTable);
}catch (Exception e){
e.printStackTrace();
}
return entityTable;
}
EntityTable时实体与表结构映射的一个简易对象.

如下,我们定义的实体

package com.dobby.code.make.model;

import com.dobby.plugins.annotation.AbolishedField;
import com.dobby.plugins.annotation.GeneratorField;
import com.dobby.plugins.annotation.GeneratorTable; import java.io.Serializable; /**
* Created by 苏若年 on 2014/11/26.
*/
//映射表别名
@GeneratorTable(name = "tb_member")
public class Member implements Serializable { //映射该字段,并且为主键,自定义字段别名
@GeneratorField(primaryKey = true, name = "m_Id")
private Integer id; @GeneratorField(name = "member_name")
private String memberName; //映射时不映射该字段
@AbolishedField
private String address; //不使用注解,默认为使用属性名进行映射
private String zipCode; //getter and setter }

查看实体映射过程

 EntityTable entityTable = BeanUtils.constructEntityTableWithPath("com.dobby.code.make.model.Member");
System.out.println("主键映射" + entityTable.getPropertyToPKey());
System.out.println("字段映射" + entityTable.getPropertyToColumn());
System.out.println("主键集合" + entityTable.getPropertyPKeyType());
System.out.println("表名映射" + entityTable.getEntityToTable());

通过注解映射后的结果如下:

主键映射{id=m_Id}
字段映射{zipCode=zipCode, memberName=member_name}
主键集合{id=java.lang.Integer}
表名映射{Member=tb_member}

因为使用了注解映射过滤,所以address字段映射时被排除.

转载请注明出处:[http://www.cnblogs.com/dennisit/p/4125103.html]

Java注解应用,自定义注解映射实现方案说明.的更多相关文章

  1. Java注解-元数据、注解分类、内置注解和自定义注解|乐字节

    大家好,我是乐字节的小乐,上次说过了Java多态的6大特性|乐字节,接下来我们来看看Java编程里的注解. Java注解有以下几个知识点: 元数据 注解的分类 内置注解 自定义注解 注解处理器 Ser ...

  2. Java中的注解及自定义注解你用的怎么样,能不能像我这样应用自如?

    Java注解提供了关于代码的一些信息,但并不直接作用于它所注解的代码内容.在这个教程当中,我们将学习Java的注解,如何定制注解,注解的使用以及如何通过反射解析注解. Java1.5引入了注解,当前许 ...

  3. Springboot--元注解及自定义注解(表单验证)

    本文简单说明一下元注解,然后对元注解中的@Retention做深入的讨论,在文章最后使用元注解写一个自定义注解来结尾. 一.结论: @Target:注解的作用目标 @Target(ElementTyp ...

  4. java注解和自定义注解的简单使用

    前言 在使用Spring Boot的时候,大量使用注解的语法去替代XML配置文件,十分好用. 然而,在使用注解的时候只知道使用,却不知道原理.直到需要用到自定义注解的时候,才发现对注解原理一无所知,所 ...

  5. Java反射与自定义注解

    反射,在Java常用框架中屡见不鲜.它存在于java.lang.reflact包中,就我的认识,它可以拿到类的字段和方法,及构造方法,还可以生成对象实例等.对深入的机制我暂时还不了解,本篇文章着重在使 ...

  6. java内置注解、元注解和自定义注解

    注解的作用: 1.生成文档 2.跟踪代码依赖性 3.编译时进行格式检查 ---------------------------------------------------------------- ...

  7. Java:深入自定义注解(Annotation)

    在网上找了很多资料也有写的比较好的,但是总有有一点半点的细节没有写出来,在这里自己总结下使用. 使用Java的自定义注解,首先个人需要了解下Java为我们提供的元注解和相关定义注解的语法.(这个我在网 ...

  8. Java注解(自定义注解、view注入)

    注解这东西虽然在jdk1.5就加进来了,但他的存在还是因为使用Afinal框架的view注入才知道的.一直觉得注入特神奇,加了一句就可以把对应view生成了. 下面我们来认识一下注解这个东西 一.注解 ...

  9. Java中的自定义注解

    ## 元注解 要声明一个注解, 我们需要元注解, 元注解是指注解的注解,包括@Retention, @Target, @Document, @Inherited. @Retention 注解的保留位置 ...

随机推荐

  1. POJ 2377 Bad Cowtractors (Kruskal)

    题意:给出一个图,求出其中的最大生成树= =如果无法产生树,输出-1. 思路:将边权降序再Kruskal,再检查一下是否只有一棵树即可,即根节点只有一个 #include <cstdio> ...

  2. 《Java程序性能优化》之并发优化

    第四章 并行程序优化 1.非阻塞同步避免了基于锁的同步的缺陷,无锁算法没有锁竞争带来的系统开销,也没有线程间频繁调度带来的开销.CAS算法:包含3个参数CAS(v,e,n).V表示要更新的变量,E表示 ...

  3. 一步一步写数据结构(二叉树的建立和遍历,c++)

    简述: 二叉树是十分重要的数据结构,主要用来存放数据,并且方便查找等操作,在很多地方有广泛的应用. 二叉树有很多种类,比如线索二叉树,二叉排序树,平衡二叉树等,本文写的是最基础最简单的二叉树. 思路: ...

  4. mac电脑对ntfs格式硬盘进行写操作(简单说就是向ntfs硬盘拷贝东西)

    使用mac电脑的童鞋应该都会遇到一个问题: 对ntfs格式的优盘或硬盘(移动硬盘默认ntfs)只能读不能写,也就是只能拷贝出数据,却没法拷贝数据到移动硬盘中. 下面是参考自网上的一种方法,无需第三方软 ...

  5. NumPy学习(索引和切片,合并,分割,copy与deep copy)

    NumPy学习(索引和切片,合并,分割,copy与deep copy) 目录 索引和切片 合并 分割 copy与deep copy 索引和切片 通过索引和切片可以访问以及修改数组元素的值 一维数组 程 ...

  6. @RequestParam注解使用:Name for argument type [java.lang.String] not available, and parameter name information not found in class file either.

    详细错误信息 Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Re ...

  7. BZOJ.1005.[HNOI2008]明明的烦恼(Prufer 高精 排列组合)

    题目链接 若点数确定那么ans = (n-2)!/[(d1-1)!(d2-1)!...(dn-1)!] 现在把那些不确定的点一起考虑(假设有m个),它们在Prufer序列中总出现数就是left=n-2 ...

  8. Android MediaPlayer架构 -- MediaPlayer的创建过程

    本文系作者自己学习之所用,文章内容仅出自作者拙劣之思考,问题之处烦请不吝指教. MediaPlayer 能被用来控制音/视频文件或流媒体的回放.Android中以MediaPlayer类作为音视频播放 ...

  9. javascript中ajax的四大步骤

    原生js中ajax写法一: function ajaxys(){ //1. 创建xhr对象 var xhr = new XMLHttpRequest();//XMLHttpRequest() // 2 ...

  10. CentOS 7下简单的Ansible使用入门

    1.配置hosts文件,Ansible依赖hosts文件进行主机通讯,不能直接在命令行上直接输入IP. vi /etc/ansible/hosts hosts文件格式如下: [servers] hos ...