java04376_Java - jdbc mybatis

jdbc

首先配置maven包

org.springframework.boot

spring-boot-starter-jdbc

org.mybatis.spring.boot

mybatis-spring-boot-starter

2.1.0

注意pom.xml中配置结点

src/main/java

**/*.xml

false

src/main/resources

static/*.*

templates/*.*

**/*.xml

**/*.yml

**/*.properties

false

针对不同的数据库,引入对应的包:SqlServer-sqljdbc4,DB2-db2jcc4,以SqlServer为例

在com.cmb.**.mapper.sqlserver目录下新建接口文件

@Repository

public interface SqlserverMapper {

List function_name();

}

同时在resources/mapperconfig/sqlserver目录下新建xml文件

select ... from ...

数据源类和工厂类配置如下

@MapperScan(basePackages = "com.cmb.**.mapper.sqlserver", sqlSessionFactoryRef = "sqlserverSqlSessionFactoryBean")

@SpringBootConfiguration

public class SqlserverDataSourceConfiguration {

private static String jdbcUrl, jdbcUser, jdbcPassword, maximumPoolSize;

static { ... }

@Bean(name = "sqlserverDataSource")

public DataSource createDataSource() {

return DataSourceConfig.getHikariDataSourceInstance(jdbcUrl, jdbcUser, jdbcPassword, maximumPoolSize);

}

}

@Configuration

public class SqlserverSessionFactoryConfiguration {

@Autowired

@Qualifier(value = "sqlserverDataSource")

private DataSource sqlserverDataSource;

private String mapperXmlConfigPath = "/mapperconfig/sqlserver/**.xml", mapperPackagePath = "com.cmb.**.mapper.sqlserver";

@Bean(name = "sqlserverSqlSessionFactoryBean")

public SqlSessionFactoryBean createSqlSessionFactory() throws Exception {

return DataSourceConfig.getSqlSessionFactoryBeanInstance(mapperXmlConfigPath, mapperPackagePath, sqlserverDataSource);

}

}

如需事务操作,上述配置类中分别新增

@Bean(name = "sqlserverTransactionManager")

@Primary

public DataSourceTransactionManager createTransactionManager(@Qualifier("sqlserverDataSource") DataSource dataSource) {

return new DataSourceTransactionManager(dataSource);

}

@Bean(name = "sqlserverSqlSessionTemplate")

@Primary

public SqlSessionTemplate createSqlSessionTemplate(@Qualifier("sqlserverSqlSessionFactoryBean") SqlSessionFactory sqlSessionFactory) {

return new SqlSessionTemplate(sqlSessionFactory);

}

public static HikariDataSource getHikariDataSourceInstance(String jdbcUrl, String jdbcUser, String jdbcPassword, String maximumPoolSize) {

HikariDataSource source = new HikariDataSource();

source.setJdbcUrl(jdbcUrl);

source.setUsername(jdbcUser);

source.setPassword(jdbcPassword);

source.setMaximumPoolSize(Integer.valueOf(maximumPoolSize));

return source;

}

public static SqlSessionFactoryBean getSqlSessionFactoryBeanInstance(String mapperXmlConfigPath, String mapperPackagePath, DataSource ds) throws Exception {

SqlSessionFactoryBean bean = new SqlSessionFactoryBean();

PathMatchingResourcePatternResolver resolver = new PathMatchingResourcePatternResolver();

String xmlConfigPath = PathMatchingResourcePatternResolver.CLASSPATH_ALL_URL_PREFIX + mapperXmlConfigPath;

bean.setMapperLocations(resolver.getResources(xmlConfigPath));//设置mapper对应的XML文件的路径

bean.setDataSource(ds);//设置数据源

bean.setTypeAliasesPackage(mapperPackagePath);//设置mapper接口所在的包

bean.getObject().getConfiguration().setMapUnderscoreToCamelCase(true);

return bean;

}

附上配置文件

- name: afvapp_hikari_sql_jdbcUrl

value: "jdbc:sqlserver://55.14.18.118:1433;DatabaseName=Business"

- name: afvapp_hikari_sql_username

value: "sa"

- name: afvapp_hikari_sql_password

value: "cmbzephyr"

- name: afvapp_hikari_sql_maximumPoolSize

value: "25"

若是mysql库,记得追加?Unicode=true&characterEncoding=UTF-8,否则部分数据库会中文乱码

mybatis

★₯₰☆ SpringBoot中设置返回类型map,值为空时字段不显示

查了几种方法,均无效...

application.properties中配置 mybatis.configuration.call-setters-on-nulls=true

最后通过配置SqlSessionFactoryBean实现:高铁直达

org.apache.ibatis.session.Configuration config = new org.apache.ibatis.session.Configuration();

config.setCallSettersOnNulls(true);

bean.setConfiguration(config);

对于字段送默认值的问题,同时设置config.setJdbcTypeForNull(JdbcType.NULL);

★₯₰☆ #{}和${}备忘

对sql语句预编译前,会动态解析为一个BoundSql对象,#{}被解析为一个参数占位符?,${}直接被纯碎的string替换

考虑到性能问题和防sql注入:

能使用#{}的地方就用#{}

表名作为变量时,必须用${}

传入数值时,select top等也建议${}

#{}:创建预处理语句属性从而设置安全的值,常用作查询条件的值、指定一个确切的数据类型

${}:不会修改或转义字符串,直接在SQL语句中插入一个不改变的字符串,常用于拼凑sql的实体部分

详情参见:动态sql中的#与$

★₯₰☆ 动态sql

先来一个mybatis的案例热热身:mybatis遇坑填坑

数据库字段binary8的问题

//sqlserver

sql语句:where UniqueID=${uniqueID},代码入参送值:"0x22CE15DD10F7F70F"

预编译后:where UniqueID=0x22CE15DD10F7F70F

//db2

sql语句:where UniqueID=x${uniqueID},代码入参送值:"'2213C85A0004376B'"

预编译后:where VerifyID=x'2213C85A0004376B'

定义resultMap通常需类型转换,须引入mybatis-typehandlers-jsr310,并配置属性typeHandler,注意要以全局限定绝对路径。通常无需指定,mybatis会自动探测。建议同时引入jackson-datatype-jsr310。

实体类字段Java.sql.Date、java.sql.Timestamp、java.util.Date映射数据库的date、timestamp、datetime字段

对mybatis返回的时间戳作格式化处理,可在ObjectMapper反序列化时统一处理,与具体数据库解耦

@Component

public class JacksonConfig {

@Bean

@Primary

public ObjectMapper objectMapper() {

ObjectMapper mapper = new ObjectMapper();

mapper.registerModule(new JSR310Module());

mapper.setDateFormat(new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS'Z'"));

return mapper;

}

}

问题:sqlserver列类型datetime,实体类字段为java.time.LocalDateTime,mybatis映射报错

1、java.util.Date可以,或直接用String

2、typeHandler="org.apache.ibatis.type.LocalDateTimeTypeHandler"无效

3、mybatis-3.5.0直接可以,无需typeHandler

第2种:mybatis-spring-boot-starter-2.1默认引入的mybatis-3.5.2抛异常且捕获不到,请求返回结果报错:3.5.x>=1均不行:mybatis 3.5.X的特性与bug

"status": 500,

"error": "Internal Server Error",

"message": "Method com/microsoft/sqlserver/jdbc/SQLServerResultSet.getObject(Ljava/lang/String;Ljava/lang/Class;)Ljava/lang/Object; is abstract",

此时需自定义TypeHandler,并typeHandler="com.cmb.afvapp.common.handler.MyLocalDateTimeTypeHandler"

public class MyLocalDateTimeTypeHandler extends LocalDateTimeTypeHandler {

@Override

public LocalDateTime getResult(ResultSet rs, String columnName) throws SQLException {

Object object = rs.getObject(columnName);

System.out.println(columnName + ": " + object);

if(object instanceof java.sql.Timestamp){//强转,将sql的时间转为LocalDateTime

return LocalDateTime.ofInstant(((Timestamp)object).toInstant(), ZoneOffset.ofHours(0));//按需转化

}

return super.getResult(rs, columnName);

}

}

关于typehandler的映射问题,参见:mybatis-typeHandlers

若遇到type-aliases-package、type-handlers-package等不起作用,导致类加载失败问题,解决:

sqlSessionFactoryBean.setVfs(SpringBootVFS.class);

★₯₰☆ 全局日期格式化问题

LocalDateTime默认ISO时间:'2011-11-03T10:15:30',提供几种格式化方法:好文参见

可以采用注解方式

@JsonSerialize(using = LocalDateTimeSerializer.class)

@JsonDeserialize(using = LocalDateTimeDeserializer.class)

@JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")

若序列化后有小时差,需json序列化时指定时区为GMT+8。

或在配置类里定义两个Bean,可完成全局日期格式化处理,同时兼顾Date和LocalDateTime并存

@Configuration

public class LocalDateTimeSerializerConfig {

@org.springframework.beans.factory.annotation.Value("${spring.jackson.date-format:yyyy-MM-dd HH:mm:ss}")

private String pattern_format;

@Bean

public LocalDateTimeSerializer localDateTimeDeserializer() {

return new LocalDateTimeSerializer(DateTimeFormatter.ofPattern(pattern_format));

}

@Bean

public Jackson2ObjectMapperBuilderCustomizer jackson2ObjectMapperBuilderCustomizer() {

return builder -> builder.serializerByType(LocalDateTime.class, localDateTimeDeserializer());

}

}

或者采用

@Bean(name = "mapperObject")

public ObjectMapper getObjectMapper() {

ObjectMapper om = new ObjectMapper();

JavaTimeModule javaTimeModule = new JavaTimeModule();

javaTimeModule.addSerializer(LocalDateTime.class, new LocalDateTimeSerializer(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));

javaTimeModule.addSerializer(LocalDate.class, new LocalDateSerializer(DateTimeFormatter.ofPattern("yyyy-MM-dd")));

javaTimeModule.addSerializer(LocalTime.class, new LocalTimeSerializer(DateTimeFormatter.ofPattern("HH:mm:ss")));

om.registerModule(javaTimeModule);

return om;

}

springboot以注解引入mybatis

注解:去XML化

★₯₰☆ 快速生成映射结果集方法

public static String getResultsStr(Class origin) {

StringBuilder stringBuilder = new StringBuilder();

stringBuilder.append("@Results({\n");

for (Field field : origin.getDeclaredFields()) {

String property = field.getName();

//映射关系:对象属性(驼峰)->数据库字段(下划线)

String column = new PropertyNamingStrategy.SnakeCaseStrategy().translate(field.getName()).toUpperCase();

stringBuilder.append(String.format("@Result(property = \"%s\", column = \"%s\"),\n", property, column));

}

stringBuilder.append("})");

return stringBuilder.toString();

}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/348396.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

设计模式 建造者模式_设计模式:建造者

设计模式 建造者模式有时需要在应用程序中创建一个复杂的对象。 一种解决方案是Factory模式,另一种是Builder设计模式。 在某些情况下,您甚至可以结合使用这两种模式。 但是在本文中,我想研究一下Builder设计模式 。 我需要说的第一件事是创造…

在MongoDB和Spring Batch中将XML转换为JSON和原始使用

总览 为什么将XML转换为JSON以在MongoDB中原始使用? 由于MongoDB使用JSON文档存储记录,就像表和行将记录存储在关系数据库中一样,我们自然需要将XML转换为JSON。 某些应用程序可能需要存储原始(未修改的)JSON&#xf…

java hash=0报空指针_怎么报空指针异常错误?

源自:2-2 开发第一个自定义标签怎么报空指针异常错误?java.lang.NullPointerExceptionat org.apache.tomcat.util.descriptor.tld.TldResourcePath.hashCode(TldResourcePath.java:164)at java.util.HashMap.hash(HashMap.java:338)at java.util.HashMap…

php 跳回上一页_php – Laravel 5 – 登录后重定向回到上一页

我有一个页面上有一些内容和评论部分.注释只能由已登录的用户保留,因此我已将登录表单添加到页面以供用户登录(仅在他们尚未登录时显示).我遇到的问题是,当用户登录时,他们会被重定向回主页,而不是他们之前所在的页面.我还没有从开箱即用的设置中更改登录方法.任何人都可以建议…

java 垃圾回收手动回收_Java垃圾回收(1)

java 垃圾回收手动回收这是有关垃圾收集(GC)的系列文章中的第一篇。 我希望能够涵盖整个系列过程中的理论知识以及热点虚拟机中的所有主要收集器。 这篇文章仅说明什么是垃圾回收以及不同回收器共有的元素。 我为什么要在乎? 您的Java虚拟机…

php mailer altbody,PHPMailer发送邮件中文乱码的解决办法

前面我们介绍了PHPMailer的使用方法和实例代码,有些朋友在使用的时候发现,发送中文邮件的时候,标题和内容中文都是乱码,这该如何解决呢?让我们先看一下之前给出的实例代码mail.php文件:require class.phpma…

使用Apache Isis快速进行SEMAT应用程序开发

TL; DR这篇文章谈论我使用Apache Isis创建并部署到此处的OpenShift Online的SEMAT宠物项目: http: //semat.ofbizian.com Apache Isis 作为主要在后端系统上工作的Java开发人员,我讨厌创建用户界面和处理Java脚本。 幸运的是,有J…

php smtp发送附件,PHP:如何使用smtp设置发送带附件的电子邮件?

发现此代码是google:// pear邮件附件搜索的首批点击之一.include(Mail.php);include(Mail/mime.php);$text Text version of email;$html HTML version of email;$file ./files/example.zip;$crlf "rn";$hdrs array(From > someonedomain.pl,To &…

java 对象锁定_少锁定Java对象池

java 对象锁定自从我写任何东西以来已经有一段时间了,我一直在忙于我的新工作,其中涉及在性能调优方面做一些有趣的工作。 挑战之一是减少应用程序关键部分的对象创建。 尽管Java随着时间的推移已改进了GC算法,但垃圾回收打ic一直是Java的主…

php怎么检查输入名称,PHP |通过$_POST []获取输入名称

HTML示例:用户填写输入字段:dfgdfg.comecho $_POST[email]; //output: dfgdfg.com表单中每个输入的名称和值都将发送到服务器.有没有办法获得名称属性?所以像..echo $_POST[email].name; //output: email编辑:澄清对我的问题的一些…

使用Speedment 3.0.17及更高版本简化交易

交易次数 有时我们想确保我们的数据库操作是原子执行的,并且与其他操作分开。 这是交易起作用的地方。 交易是一组操作 数据库可能接受或不接受作为原子操作的建议。 因此,要么接受交易中的所有操作,要么不接受交易中的所有操作。 事务的另一…

图像二值化 php im2bw,图像二值化-MATLAB实现

1.图像二值化代码:Aimread(hw1.chips1.GIF); %读取到一张图片%thresh graythresh(A); %自动确定二值化阈值I2 im2bw(A,120/255); %对图像二值化figure();subplot(1,2,1);imshow(A); %显示二值化之前的图片title(原图);subplot(1,2,2);imshow(I2); %显示二值化之后…

Linux操作系统基础

前言 当涉及到计算机操作系统时,Linux 是一个备受关注和广泛使用的开源操作系统。Linux 操作系统以其灵活性、可定制性和强大的性能而闻名,并且在各个领域都有广泛的应用,从服务器和嵌入式设备到个人电脑和移动设备。 本文将介绍 Linux 操作…

php laravel 调试,php – Xdebug laravel artisan命令

我经常使用xdebug来调试应用程序,我已经构建了一个laravel应用程序,它可以上传一个csv,将数据插入到数据库中,并将id输入到作业队列中.我写了一个工匠命令,通过cron运行,然后对这些数据做一些事情.Xdebug适用于通过浏览器访问该站点,但从cli运行时它不会破坏断点.我运行php5-fp…

Spring MVC:高级会话

不久前,我写了一篇关于Spring MVC应用程序中HTTP会话的文章。 那是简单的文章,着重于用法的实际方面。 在文章的最后,我保证会写一些更高级的主题,专门针对Spring MVC应用程序中的会话。 因此,我将发布这些东西。 在开…

php node 目录,node.js基于fs模块对系统文件及目录进行读写操作的方法详解

本文主要介绍了node.js基于fs模块对系统文件及目录进行读写操作的方法,结合实例形式分析了nodejs使用fs模块针对文件与目录的读写、创建、删除等相关操作技巧,需要的朋友可以参考下。如果要用这个模块,首先需要引入,fs已经属于node.js自带的模块&#xf…

Oracle JDBC中的PreparedStatement占位符过多

使用Oracle数据库时,导致ORA-01745(“无效的主机/绑定变量名称错误”)错误的原因有多种。 关于错误ORA-01500到ORA-02098的Oracle 9i文档提供了有关ORA-01745的更多详细信息。 它指出,“原因”是“绑定变量或INTO规范中的冒号后跟…

webview加载php文件,HYWebview下载自定义文件教程

车机版 HYWebview升级到1.3了多增加了一个进度条多增加了自定义下载URL功能使用教程。浏览器打开DNS地址:103.44.248.95可见 底部有一个 下载链接 和 提货密码 可以输入!比如 我们去应用宝官网复制下载链接出来:https://download.sj.qq.com/u…

php-fpm7.0,php-fpm7.0 慢查询设置及说明

环境说明rootubuntu:/home/tb# cat /etc/issue Ubuntu 16.04.2 LTS \n \l rootubuntu:/home/tb# php -v PHP 7.0.15-0ubuntu0.16.04.4 (cli) ( NTS ) Copyright (c) 1997-2017 The PHP Group Zend Engine v3.0.0, Copyright (c) 1998-2017 Zend Technologies with Zend OPcache…

设计模式 原型模式_设计模式:原型

设计模式 原型模式创新设计模式之一是原型设计模式 。 尽管原型是创造模式,但它在概念上与其他模式有所区别。 我的意思是原型在某种意义上创造了自己。 我将在下面解释。 原型模式的所有魔力都基于Java Object的clone()方法。 因此&#x…