Spring 事务core 模块-元数据metaData 模块

 CallMetaDataProviderFactory 创建CallMetaDataProvider 的工厂类,其代码如下:

public class CallMetaDataProviderFactory {
    public static final List<String> supportedDatabaseProductsForProcedures = Arrays.asList("Apache Derby", "DB2", "MySQL", "Microsoft SQL Server", "Oracle", "PostgreSQL", "Sybase");
    public static final List<String> supportedDatabaseProductsForFunctions = Arrays.asList("MySQL", "Microsoft SQL Server", "Oracle", "PostgreSQL");
    private static final Log logger = LogFactory.getLog(CallMetaDataProviderFactory.class);

    public CallMetaDataProviderFactory() {
    }

    public static CallMetaDataProvider createMetaDataProvider(DataSource dataSource, CallMetaDataContext context) {
        try {
            CallMetaDataProvider result = (CallMetaDataProvider)JdbcUtils.extractDatabaseMetaData(dataSource, (databaseMetaData) -> {
                String databaseProductName = JdbcUtils.commonDatabaseName(databaseMetaData.getDatabaseProductName());
                boolean accessProcedureColumnMetaData = context.isAccessCallParameterMetaData();
                if (context.isFunction()) {
                    if (!supportedDatabaseProductsForFunctions.contains(databaseProductName)) {
                        if (logger.isWarnEnabled()) {
                            logger.warn(databaseProductName + " is not one of the databases fully supported for function calls -- supported are: " + supportedDatabaseProductsForFunctions);
                        }

                        if (accessProcedureColumnMetaData) {
                            logger.warn("Metadata processing disabled - you must specify all parameters explicitly");
                            accessProcedureColumnMetaData = false;
                        }
                    }
                } else if (!supportedDatabaseProductsForProcedures.contains(databaseProductName)) {
                    if (logger.isWarnEnabled()) {
                        logger.warn(databaseProductName + " is not one of the databases fully supported for procedure calls -- supported are: " + supportedDatabaseProductsForProcedures);
                    }

                    if (accessProcedureColumnMetaData) {
                        logger.warn("Metadata processing disabled - you must specify all parameters explicitly");
                        accessProcedureColumnMetaData = false;
                    }
                }

                Object provider;
                if ("Oracle".equals(databaseProductName)) {
                    provider = new OracleCallMetaDataProvider(databaseMetaData);
                } else if ("DB2".equals(databaseProductName)) {
                    provider = new Db2CallMetaDataProvider(databaseMetaData);
                } else if ("Apache Derby".equals(databaseProductName)) {
                    provider = new DerbyCallMetaDataProvider(databaseMetaData);
                } else if ("PostgreSQL".equals(databaseProductName)) {
                    provider = new PostgresCallMetaDataProvider(databaseMetaData);
                } else if ("Sybase".equals(databaseProductName)) {
                    provider = new SybaseCallMetaDataProvider(databaseMetaData);
                } else if ("Microsoft SQL Server".equals(databaseProductName)) {
                    provider = new SqlServerCallMetaDataProvider(databaseMetaData);
                } else if ("HDB".equals(databaseProductName)) {
                    provider = new HanaCallMetaDataProvider(databaseMetaData);
                } else {
                    provider = new GenericCallMetaDataProvider(databaseMetaData);
                }

                if (logger.isDebugEnabled()) {
                    logger.debug("Using " + provider.getClass().getName());
                }

                ((CallMetaDataProvider)provider).initializeWithMetaData(databaseMetaData);
                if (accessProcedureColumnMetaData) {
                    ((CallMetaDataProvider)provider).initializeWithProcedureColumnMetaData(databaseMetaData, context.getCatalogName(), context.getSchemaName(), context.getProcedureName());
                }

                return provider;
            });
            return result;
        } catch (MetaDataAccessException var3) {
            throw new DataAccessResourceFailureException("Error retrieving database metadata", var3);
        }
    }
}

TableMetaDataProviderFactory 创建TableMetaDataProvider 工厂类,其创建过程如下:

public static TableMetaDataProvider createMetaDataProvider(DataSource dataSource, TableMetaDataContext context) {
	try {
		TableMetaDataProvider result = (TableMetaDataProvider)JdbcUtils.extractDatabaseMetaData(dataSource, (databaseMetaData) -> {
			String databaseProductName = JdbcUtils.commonDatabaseName(databaseMetaData.getDatabaseProductName());
			boolean accessTableColumnMetaData = context.isAccessTableColumnMetaData();
			Object provider;
			if ("Oracle".equals(databaseProductName)) {
				provider = new OracleTableMetaDataProvider(databaseMetaData, context.isOverrideIncludeSynonymsDefault());
			} else if ("HSQL Database Engine".equals(databaseProductName)) {
				provider = new HsqlTableMetaDataProvider(databaseMetaData);
			} else if ("PostgreSQL".equals(databaseProductName)) {
				provider = new PostgresTableMetaDataProvider(databaseMetaData);
			} else if ("Apache Derby".equals(databaseProductName)) {
				provider = new DerbyTableMetaDataProvider(databaseMetaData);
			} else {
				provider = new GenericTableMetaDataProvider(databaseMetaData);
			}

			if (logger.isDebugEnabled()) {
				logger.debug("Using " + provider.getClass().getSimpleName());
			}

			((TableMetaDataProvider)provider).initializeWithMetaData(databaseMetaData);
			if (accessTableColumnMetaData) {
				((TableMetaDataProvider)provider).initializeWithTableColumnMetaData(databaseMetaData, context.getCatalogName(), context.getSchemaName(), context.getTableName());
			}

			return provider;
		});
		return result;
	} catch (MetaDataAccessException var3) {
		throw new DataAccessResourceFailureException("Error retrieving database metadata", var3);
	}
}

使用SqlParameterSource 提供参数值

使用Map 来指定参数值有时候工作得非常好,但是这并不是最简单的使用方式。Spring提供了一些其他的SqlParameterSource 实现类来指定参数值。我们首先可以看看BeanPropertySqlParameterSource 类,这是一个非常简便的指定参数的实现类,只要你有一个符合JavaBean 规范的类就行了。它将使用其中的getter 方法来获取参数值。

SqlParameter 封装了定义sql 参数的对象。CallableStateMentCallback ,PrePareStateMentCallback,StateMentCallback,ConnectionCallback 回调类分别对应JdbcTemplate 中的不同处理方法。

simple 实现

Spring 通过DataSource 获取数据库的连接。Datasource 是jdbc 规范的一部分,它通过ConnectionFactory 获取。一个容器和框架可以在应用代码层中隐藏连接池和事务管理。

当使用spring 的jdbc 层,你可以通过JNDI 来获取DataSource,也可以通过你自己配置的第三方连接池实现来获取。流行的第三方实现由apache Jakarta Commons dbcp 和c3p0。

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值