Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance. Project price only 1 $
You can buy this project and download/modify it how often you want.
/**
* Copyright (c) 2015-2022, Michael Yang 杨福海 ([email protected]).
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.jboot.db.model;
import com.jfinal.kit.LogKit;
import com.jfinal.log.Log;
import com.jfinal.plugin.activerecord.*;
import com.jfinal.plugin.activerecord.dialect.Dialect;
import io.jboot.db.JbootDb;
import io.jboot.db.SqlDebugger;
import io.jboot.db.dialect.JbootDialect;
import io.jboot.exception.JbootException;
import io.jboot.exception.JbootIllegalConfigException;
import io.jboot.utils.ClassUtil;
import io.jboot.utils.StrUtil;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.*;
/**
* @author michael yang
*/
public class JbootModel> extends Model {
private static final Log LOG = Log.getLog(JbootModel.class);
private static final String DATASOURCE_CACHE_PREFIX = "__ds__";
private static JbootModelConfig config = JbootModelConfig.getConfig();
private static String column_created = config.getColumnCreated();
private static String column_modified = config.getColumnModified();
private static boolean idCacheEnable = config.isIdCacheEnable();
protected List joins = null;
String datasourceName = null;
String alias = null;
String loadColumns = null;
boolean isCopyModel = false;
public Joiner leftJoin(String table) {
return joining(Join.TYPE_LEFT, table, true);
}
public Joiner leftJoinIf(String table, boolean condition) {
return joining(Join.TYPE_LEFT, table, condition);
}
public Joiner rightJoin(String table) {
return joining(Join.TYPE_RIGHT, table, true);
}
public Joiner rightJoinIf(String table, boolean condition) {
return joining(Join.TYPE_RIGHT, table, condition);
}
public Joiner innerJoin(String table) {
return joining(Join.TYPE_INNER, table, true);
}
public Joiner innerJoinIf(String table, boolean condition) {
return joining(Join.TYPE_INNER, table, condition);
}
public Joiner fullJoin(String table) {
return joining(Join.TYPE_FULL, table, true);
}
public Joiner fullJoinIf(String table, boolean condition) {
return joining(Join.TYPE_FULL, table, condition);
}
/**
* set table alias in sql
*
* @param alias
* @return
*/
public M alias(String alias) {
if (StrUtil.isBlank(alias)) {
throw new IllegalArgumentException("alias must not be null or empty.");
}
M model = getOrCopyDao();
model.alias = alias;
return model;
}
protected Joiner joining(String type, String table, boolean condition) {
M model = getOrCopyDao();
if (model.joins == null) {
model.joins = new LinkedList<>();
}
Join join = new Join(type, table, condition);
model.joins.add(join);
return new Joiner<>(model, join);
}
/**
* set load columns in sql
*
* @param loadColumns
* @return
*/
public M loadColumns(String loadColumns) {
if (StrUtil.isBlank(loadColumns)) {
throw new IllegalArgumentException("loadColumns must not be null or empty.");
}
M model = getOrCopyDao();
model.loadColumns = loadColumns;
return model;
}
public M distinct(String columnName) {
if (StrUtil.isBlank(columnName)) {
throw new IllegalArgumentException("columnName must not be null or empty.");
}
M dao = getOrCopyDao();
JbootModelExts.setDistinctColumn(dao, columnName);
return dao;
}
private M getOrCopyDao() {
if (isCopyModel) {
return (M) this;
} else {
M dao = copy()._setConfigName(datasourceName);
dao.isCopyModel = true;
return dao;
}
}
@Override
public M dao() {
put("__is_dao", true);
return (M) this;
}
private boolean isDaoModel() {
Boolean flag = getBoolean("__is_dao");
return flag != null && flag;
}
/**
* copy model with attrs or false
*
* @return
*/
public M copy() {
M m = null;
try {
m = (M) _getUsefulClass().newInstance();
m.put(_getAttrs());
for (String attr : _getModifyFlag()) {
m._getModifyFlag().add(attr);
}
} catch (Exception e) {
LOG.error(e.toString(), e);
}
return m;
}
/**
* copy new model with db attrs and fill modifyFlag
*
* @return
*/
public M copyModel() {
M m = null;
try {
m = (M) _getUsefulClass().newInstance();
Table table = _getTable(true);
Set attrKeys = table.getColumnTypeMap().keySet();
for (String attrKey : attrKeys) {
Object o = this.get(attrKey);
if (o != null) {
m.set(attrKey, o);
}
}
} catch (Exception e) {
LOG.error(e.toString(), e);
}
return m;
}
/**
* 修复 JFinal use 造成的线程安全问题
*
* @param configName
* @return
*/
@Override
public M use(String configName) {
return use(configName, true);
}
/**
* 优先使用哪个数据源进行查询
*
* @param configNames
* @return
*/
public M useFirst(String... configNames) {
if (configNames == null || configNames.length == 0) {
throw new IllegalArgumentException("configNames must not be null or empty.");
}
for (String name : configNames) {
M newDao = use(name, false);
if (newDao != null) {
return newDao;
}
}
return (M) this;
}
private M use(String configName, boolean validateDatasourceExist) {
//非 service 的 dao,例如 new User().user('ds').save()/upate()
if (!isDaoModel()) {
_setConfigName(configName);
return validDatasourceExist((M) this, validateDatasourceExist, configName);
}
//定义在 service 中的 DAO
M newDao = JbootModelExts.getDatasourceDAO(this, DATASOURCE_CACHE_PREFIX + configName);
if (newDao == null) {
newDao = this.copy()._setConfigName(configName);
newDao = validDatasourceExist(newDao, validateDatasourceExist, configName);
if (newDao != null) {
JbootModelExts.setDatasourceDAO(this, DATASOURCE_CACHE_PREFIX + configName, newDao);
}
}
return newDao;
}
private M validDatasourceExist(M model, boolean valid, String configName) {
if (model._getConfig() == null) {
if (valid) {
throw new JbootIllegalConfigException("The datasource \"" + configName + "\" not config well, please config it in jboot.properties.");
} else {
return null;
}
}
return model;
}
M _setConfigName(String configName) {
this.datasourceName = configName;
return (M) this;
}
@Override
protected Config _getConfig() {
if (datasourceName != null) {
return DbKit.getConfig(datasourceName);
}
String currentConfigName = JbootDb.getCurrentConfigName();
if (StrUtil.isNotBlank(currentConfigName)) {
Config config = DbKit.getConfig(currentConfigName);
if (config == null) {
LogKit.error("Can not use the datasource: {}, user default to replace.", currentConfigName);
} else {
return config;
}
}
return DbKit.getConfig(_getUsefulClass());
}
public boolean saveOrUpdate() {
if (null == _getIdValue()) {
return this.save();
}
return this.update();
}
@Override
public boolean save() {
if (_hasColumn(column_created) && get(column_created) == null) {
set(column_created, new Date());
}
// 生成主键,只对单一主键的表生成,如果是多主键,不生成。
String[] pkeys = _getPrimaryKeys();
if (pkeys != null && pkeys.length == 1 && get(pkeys[0]) == null) {
Object value = config.getPrimarykeyValueGenerator().genValue(this, _getPrimaryType());
if (value != null) {
set(pkeys[0], value);
}
}
filter(FILTER_BY_SAVE);
Config config = _getConfig();
Table table = _getTable();
StringBuilder sql = new StringBuilder();
List