This commit is contained in:
地平线
2015-07-21 11:03:18 +08:00
parent 54a7c94cf5
commit 29e5695060
9 changed files with 357 additions and 291 deletions

View File

@@ -180,7 +180,7 @@ public final class Application {
final File root = new File(System.getProperty(RESNAME_HOME)); final File root = new File(System.getProperty(RESNAME_HOME));
File persist = new File(root, "conf/persistence.xml"); File persist = new File(root, "conf/persistence.xml");
if (persist.isFile()) System.setProperty(DataJDBCSource.DATASOURCE_CONFPATH, persist.getCanonicalPath()); if (persist.isFile()) System.setProperty(DataDefaultSource.DATASOURCE_CONFPATH, persist.getCanonicalPath());
logger.log(Level.INFO, RESNAME_HOME + "=" + root.getCanonicalPath() + "\r\n" + RESNAME_ADDR + "=" + this.localAddress.getHostAddress()); logger.log(Level.INFO, RESNAME_HOME + "=" + root.getCanonicalPath() + "\r\n" + RESNAME_ADDR + "=" + this.localAddress.getHostAddress());
String lib = config.getValue("lib", "").trim().replace("${APP_HOME}", root.getCanonicalPath()); String lib = config.getValue("lib", "").trim().replace("${APP_HOME}", root.getCanonicalPath());
lib = lib.isEmpty() ? (root.getCanonicalPath() + "/conf") : (lib + ";" + root.getCanonicalPath() + "/conf"); lib = lib.isEmpty() ? (root.getCanonicalPath() + "/conf") : (lib + ";" + root.getCanonicalPath() + "/conf");

View File

@@ -92,27 +92,21 @@ public final class HttpResourceServlet extends HttpServlet {
protected WatchThread watchThread; protected WatchThread watchThread;
protected List<SimpleEntry<File, WatchThread>> resx;
protected Predicate<String> ranges; protected Predicate<String> ranges;
@Override @Override
public void init(Context context, AnyValue config) { public void init(Context context, AnyValue config) {
String[] rootstrs = null;
if (config != null) { if (config != null) {
rootstrs = config.getValue("webroot", "root").trim().split(";"); String rootstr = config.getValue("webroot", "root");
for (int i = 0; i < rootstrs.length; i++) {
String rootstr = rootstrs[i];
if (rootstr.indexOf(':') < 0 && rootstr.indexOf('/') != 0 && System.getProperty("APP_HOME") != null) { if (rootstr.indexOf(':') < 0 && rootstr.indexOf('/') != 0 && System.getProperty("APP_HOME") != null) {
rootstrs[i] = new File(System.getProperty("APP_HOME"), rootstr).getPath(); rootstr = new File(System.getProperty("APP_HOME"), rootstr).getPath();
}
} }
String rangesValue = config.getValue("ranges"); String rangesValue = config.getValue("ranges");
this.ranges = rangesValue != null ? Pattern.compile(rangesValue).asPredicate() : null; this.ranges = rangesValue != null ? Pattern.compile(rangesValue).asPredicate() : null;
try { try {
this.root = new File(rootstrs[0]).getCanonicalFile(); this.root = new File(rootstr).getCanonicalFile();
} catch (IOException ioe) { } catch (IOException ioe) {
this.root = new File(rootstrs[0]); this.root = new File(rootstr);
} }
AnyValue cacheconf = config.getAnyValue("caches"); AnyValue cacheconf = config.getAnyValue("caches");
if (cacheconf != null) { if (cacheconf != null) {
@@ -131,7 +125,7 @@ public final class HttpResourceServlet extends HttpServlet {
} }
this.locationRewrites = locations.isEmpty() ? null : locations.toArray(new SimpleEntry[locations.size()]); this.locationRewrites = locations.isEmpty() ? null : locations.toArray(new SimpleEntry[locations.size()]);
} }
if (this.cachelimit < 1) return; if (this.cachelimit < 1) return; //不缓存不需要开启WatchThread监听
if (this.root != null) { if (this.root != null) {
try { try {
this.watchThread = new WatchThread(this.root); this.watchThread = new WatchThread(this.root);
@@ -139,19 +133,6 @@ public final class HttpResourceServlet extends HttpServlet {
} catch (IOException ex) { } catch (IOException ex) {
logger.log(Level.WARNING, HttpResourceServlet.class.getSimpleName() + " start watch-thread error", ex); logger.log(Level.WARNING, HttpResourceServlet.class.getSimpleName() + " start watch-thread error", ex);
} }
if (rootstrs != null && rootstrs.length > 1) {
resx = new ArrayList<>(rootstrs.length - 1);
for (int i = 1; i < rootstrs.length; i++) {
try {
File f = new File(rootstrs[i]).getCanonicalFile();
WatchThread t = new WatchThread(f);
t.start();
resx.add(new SimpleEntry<>(f, t));
} catch (IOException ioe) {
ioe.printStackTrace();
}
}
}
} }
} }
@@ -193,10 +174,15 @@ public final class HttpResourceServlet extends HttpServlet {
} }
if (uri.length() == 0 || uri.equals("/")) uri = "/index.html"; if (uri.length() == 0 || uri.equals("/")) uri = "/index.html";
//System.out.println(request); //System.out.println(request);
FileEntry entry = watchThread == null ? createFileEntry(uri) : files.get(uri); FileEntry entry;
if (watchThread == null) {
entry = createFileEntry(uri);
} else { //有缓存
entry = files.get(uri);
if (entry == null) { if (entry == null) {
entry = createFileEntry(uri); entry = createFileEntry(uri);
if (entry != null && watchThread != null) files.put(uri, entry); if (entry != null) files.put(uri, entry);
}
} }
if (entry == null) { if (entry == null) {
response.finish404(); response.finish404();
@@ -207,32 +193,15 @@ public final class HttpResourceServlet extends HttpServlet {
private FileEntry createFileEntry(String uri) { private FileEntry createFileEntry(String uri) {
File file = new File(root, uri); File file = new File(root, uri);
if (!file.isFile() || !file.canRead()) { if (file.isDirectory()) file = new File(file, "index.html");
if (resx != null) { if (!file.isFile() || !file.canRead()) return null;
for (SimpleEntry<File, WatchThread> en : resx) {
File f = new File(en.getKey(), uri);
if (f.isFile() && f.canRead()) {
FileEntry fe = new FileEntry(this, f);
if (watchThread == null) return fe;
try {
Path p = f.getParentFile().toPath();
keymaps.put(p.register(en.getValue().watcher, ENTRY_MODIFY, ENTRY_DELETE), p);
} catch (IOException e) {
logger.log(Level.INFO, HttpResourceServlet.class.getSimpleName() + " create FileEntry(" + uri + ") erroneous", e);
}
return fe;
}
}
}
return null;
}
FileEntry en = new FileEntry(this, file); FileEntry en = new FileEntry(this, file);
if (watchThread == null) return en; if (watchThread == null) return en;
try { try {
Path p = file.getParentFile().toPath(); Path p = file.getParentFile().toPath();
keymaps.put(p.register(watchThread.watcher, ENTRY_MODIFY, ENTRY_DELETE), p); keymaps.put(p.register(watchThread.watcher, ENTRY_MODIFY, ENTRY_DELETE), p);
} catch (IOException e) { } catch (IOException e) {
logger.log(Level.INFO, HttpResourceServlet.class.getSimpleName() + " create FileEntry(" + uri + ") erroneous", e); logger.log(Level.INFO, HttpResourceServlet.class.getSimpleName() + " watch FileEntry(" + uri + ") erroneous", e);
} }
return en; return en;
} }
@@ -258,7 +227,7 @@ public final class HttpResourceServlet extends HttpServlet {
} }
long length = this.file.length(); long length = this.file.length();
if (length > this.servlet.cachelengthmax) return; if (length > this.servlet.cachelengthmax) return;
if (this.servlet.cachedLength.longValue() + length > this.servlet.cachelimit) return; if (this.servlet.cachedLength.longValue() + length > this.servlet.cachelimit) return; //超过缓存总容量
try { try {
FileInputStream in = new FileInputStream(file); FileInputStream in = new FileInputStream(file);
ByteArrayOutputStream out = new ByteArrayOutputStream((int) file.length()); ByteArrayOutputStream out = new ByteArrayOutputStream((int) file.length());

View File

@@ -133,7 +133,7 @@ public class DataCacheListenerService implements DataCacheListener, Service {
public final <T> void onSendInsert(String group, boolean ignoreRemote, String sourceName, Class<T> clazz, T... entitys) { public final <T> void onSendInsert(String group, boolean ignoreRemote, String sourceName, Class<T> clazz, T... entitys) {
if (finest) logger.finest(DataSource.class.getSimpleName() + "(" + this.localNodeName + "," + sourceName + ") onSendInsert " + Arrays.toString(entitys)); if (finest) logger.finest(DataSource.class.getSimpleName() + "(" + this.localNodeName + "," + sourceName + ") onSendInsert " + Arrays.toString(entitys));
((DataJDBCSource) sourcesmap.get(sourceName)).insertCache(entitys); ((DataDefaultSource) sourcesmap.get(sourceName)).insertCache(entitys);
if (!this.localGroupName.equals(group)) sendInsert(this.localGroupName, true, sourceName, clazz, entitys); //不是同一机房来的资源需要同步到其他同机房的节点上 if (!this.localGroupName.equals(group)) sendInsert(this.localGroupName, true, sourceName, clazz, entitys); //不是同一机房来的资源需要同步到其他同机房的节点上
} }
@@ -213,7 +213,7 @@ public class DataCacheListenerService implements DataCacheListener, Service {
public final <T> void onSendUpdate(String group, boolean ignoreRemote, String sourceName, Class<T> clazz, T... entitys) { public final <T> void onSendUpdate(String group, boolean ignoreRemote, String sourceName, Class<T> clazz, T... entitys) {
if (finest) logger.finest(DataSource.class.getSimpleName() + "(" + group + "--" + this.localNodeName + "," + sourceName + ") onSendUpdate " + Arrays.toString(entitys)); if (finest) logger.finest(DataSource.class.getSimpleName() + "(" + group + "--" + this.localNodeName + "," + sourceName + ") onSendUpdate " + Arrays.toString(entitys));
((DataJDBCSource) sourcesmap.get(sourceName)).updateCache(clazz, entitys); ((DataDefaultSource) sourcesmap.get(sourceName)).updateCache(clazz, entitys);
if (!this.localGroupName.equals(group)) sendUpdate(this.localGroupName, true, sourceName, clazz, entitys); //不是同一机房来的资源需要同步到其他同机房的节点上 if (!this.localGroupName.equals(group)) sendUpdate(this.localGroupName, true, sourceName, clazz, entitys); //不是同一机房来的资源需要同步到其他同机房的节点上
} }
@@ -293,7 +293,7 @@ public class DataCacheListenerService implements DataCacheListener, Service {
public final <T> void onSendDelete(String group, boolean ignoreRemote, String sourceName, Class<T> clazz, Serializable... ids) { public final <T> void onSendDelete(String group, boolean ignoreRemote, String sourceName, Class<T> clazz, Serializable... ids) {
if (finest) logger.finest(DataSource.class.getSimpleName() + "(" + group + "--" + this.localNodeName + "," + sourceName + ") onSendDelete " + clazz.getName() + " " + Arrays.toString(ids)); if (finest) logger.finest(DataSource.class.getSimpleName() + "(" + group + "--" + this.localNodeName + "," + sourceName + ") onSendDelete " + clazz.getName() + " " + Arrays.toString(ids));
((DataJDBCSource) sourcesmap.get(sourceName)).deleteCache(clazz, ids); ((DataDefaultSource) sourcesmap.get(sourceName)).deleteCache(clazz, ids);
if (!this.localGroupName.equals(group)) sendDelete(this.localGroupName, true, sourceName, clazz, ids); //不是同一机房来的资源需要同步到其他同机房的节点上 if (!this.localGroupName.equals(group)) sendDelete(this.localGroupName, true, sourceName, clazz, ids); //不是同一机房来的资源需要同步到其他同机房的节点上
} }
} }

View File

@@ -7,7 +7,7 @@ package com.wentch.redkale.service;
import com.wentch.redkale.source.DataSQLListener; import com.wentch.redkale.source.DataSQLListener;
import com.wentch.redkale.source.DataSource; import com.wentch.redkale.source.DataSource;
import com.wentch.redkale.source.DataJDBCSource; import com.wentch.redkale.source.DataDefaultSource;
import com.wentch.redkale.util.AnyValue; import com.wentch.redkale.util.AnyValue;
import com.wentch.redkale.util.AutoLoad; import com.wentch.redkale.util.AutoLoad;
import java.io.*; import java.io.*;
@@ -172,7 +172,7 @@ public class DataSQLListenerService implements DataSQLListener, Service {
} }
public final void onSend(String sourceName, String... sqls) { public final void onSend(String sourceName, String... sqls) {
((DataJDBCSource) sourcemaps.get(sourceName)).execute(sqls); ((DataDefaultSource) sourcemaps.get(sourceName)).execute(sqls);
} }
} }

View File

@@ -24,7 +24,7 @@ import javax.xml.stream.*;
* @author zhangjx * @author zhangjx
*/ */
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
public final class DataJDBCSource implements DataSource { public final class DataDefaultSource implements DataSource {
public static final String DATASOURCE_CONFPATH = "DATASOURCE_CONFPATH"; public static final String DATASOURCE_CONFPATH = "DATASOURCE_CONFPATH";
@@ -42,7 +42,7 @@ public final class DataJDBCSource implements DataSource {
private static final Flipper FLIPPER_ONE = new Flipper(1); private static final Flipper FLIPPER_ONE = new Flipper(1);
final Logger logger = Logger.getLogger(DataJDBCSource.class.getSimpleName()); final Logger logger = Logger.getLogger(DataDefaultSource.class.getSimpleName());
final AtomicBoolean debug = new AtomicBoolean(logger.isLoggable(Level.FINEST)); final AtomicBoolean debug = new AtomicBoolean(logger.isLoggable(Level.FINEST));
@@ -55,13 +55,13 @@ public final class DataJDBCSource implements DataSource {
private final JDBCPoolSource writePool; private final JDBCPoolSource writePool;
@Resource(name = "property.datasource.nodeid") @Resource(name = "property.datasource.nodeid")
int nodeid; private int nodeid;
@Resource @Resource
DataSQLListener writeListener; private DataSQLListener writeListener;
@Resource @Resource
DataCacheListener cacheListener; private DataCacheListener cacheListener;
private static class DataJDBCConnection extends DataConnection { private static class DataJDBCConnection extends DataConnection {
@@ -108,17 +108,17 @@ public final class DataJDBCSource implements DataSource {
private final Function<Class, List> fullloader = (t) -> queryList(t, (FilterNode) null); private final Function<Class, List> fullloader = (t) -> queryList(t, (FilterNode) null);
public DataJDBCSource() throws IOException { public DataDefaultSource() throws IOException {
this(""); this("");
} }
public DataJDBCSource(final String unitName) throws IOException { public DataDefaultSource(final String unitName) throws IOException {
this(unitName, System.getProperty(DATASOURCE_CONFPATH) == null this(unitName, System.getProperty(DATASOURCE_CONFPATH) == null
? DataJDBCSource.class.getResource("/META-INF/persistence.xml") ? DataDefaultSource.class.getResource("/META-INF/persistence.xml")
: new File(System.getProperty(DATASOURCE_CONFPATH)).toURI().toURL()); : new File(System.getProperty(DATASOURCE_CONFPATH)).toURI().toURL());
} }
public DataJDBCSource(final String unitName, URL url) throws IOException { public DataDefaultSource(final String unitName, URL url) throws IOException {
if (url == null) url = this.getClass().getResource("/persistence.xml"); if (url == null) url = this.getClass().getResource("/persistence.xml");
InputStream in = url.openStream(); InputStream in = url.openStream();
Map<String, Properties> map = loadProperties(in); Map<String, Properties> map = loadProperties(in);
@@ -156,7 +156,7 @@ public final class DataJDBCSource implements DataSource {
EntityInfo.cacheForbidden = "NONE".equalsIgnoreCase(readprop.getProperty("shared-cache-mode")); EntityInfo.cacheForbidden = "NONE".equalsIgnoreCase(readprop.getProperty("shared-cache-mode"));
} }
public DataJDBCSource(String unitName, Properties readprop, Properties writeprop) { public DataDefaultSource(String unitName, Properties readprop, Properties writeprop) {
this.name = unitName; this.name = unitName;
this.conf = null; this.conf = null;
this.readPool = new JDBCPoolSource(this, "read", readprop); this.readPool = new JDBCPoolSource(this, "read", readprop);
@@ -164,7 +164,7 @@ public final class DataJDBCSource implements DataSource {
EntityInfo.cacheForbidden = "NONE".equalsIgnoreCase(readprop.getProperty("shared-cache-mode")); EntityInfo.cacheForbidden = "NONE".equalsIgnoreCase(readprop.getProperty("shared-cache-mode"));
} }
public static Map<String, DataJDBCSource> create(final InputStream in) { public static Map<String, DataDefaultSource> create(final InputStream in) {
Map<String, Properties> map = loadProperties(in); Map<String, Properties> map = loadProperties(in);
Map<String, Properties[]> maps = new HashMap<>(); Map<String, Properties[]> maps = new HashMap<>();
map.entrySet().stream().forEach((en) -> { map.entrySet().stream().forEach((en) -> {
@@ -179,9 +179,9 @@ public final class DataJDBCSource implements DataSource {
maps.put(en.getKey(), new Properties[]{en.getValue(), en.getValue()}); maps.put(en.getKey(), new Properties[]{en.getValue(), en.getValue()});
} }
}); });
Map<String, DataJDBCSource> result = new HashMap<>(); Map<String, DataDefaultSource> result = new HashMap<>();
maps.entrySet().stream().forEach((en) -> { maps.entrySet().stream().forEach((en) -> {
result.put(en.getKey(), new DataJDBCSource(en.getKey(), en.getValue()[0], en.getValue()[1])); result.put(en.getKey(), new DataDefaultSource(en.getKey(), en.getValue()[0], en.getValue()[1]));
}); });
return result; return result;
} }
@@ -280,11 +280,12 @@ public final class DataJDBCSource implements DataSource {
return readPool.poll(); return readPool.poll();
} }
private Connection createWriteSQLConnection() { private <T> Connection createWriteSQLConnection() {
return writePool.poll(); return writePool.poll();
} }
private void closeSQLConnection(final Connection sqlconn) { private void closeSQLConnection(final Connection sqlconn) {
if (sqlconn == null) return;
try { try {
sqlconn.close(); sqlconn.close();
} catch (Exception e) { } catch (Exception e) {
@@ -349,9 +350,15 @@ public final class DataJDBCSource implements DataSource {
*/ */
@Override @Override
public <T> void insert(T... values) { public <T> void insert(T... values) {
if (values.length == 0) return;
final EntityInfo<T> info = loadEntityInfo((Class<T>) values[0].getClass());
if (info.isVirtualEntity()) {
insert(null, info, values);
return;
}
Connection conn = createWriteSQLConnection(); Connection conn = createWriteSQLConnection();
try { try {
insert(conn, values); insert(conn, info, values);
} finally { } finally {
closeSQLConnection(conn); closeSQLConnection(conn);
} }
@@ -366,17 +373,18 @@ public final class DataJDBCSource implements DataSource {
*/ */
@Override @Override
public <T> void insert(final DataConnection conn, T... values) { public <T> void insert(final DataConnection conn, T... values) {
insert((Connection) conn.getConnection(), values); if (values.length == 0) return;
final EntityInfo<T> info = loadEntityInfo((Class<T>) values[0].getClass());
insert((Connection) conn.getConnection(), info, values);
} }
private <T> void insert(final Connection conn, T... values) { private <T> void insert(final Connection conn, final EntityInfo<T> info, T... values) {
if (values.length == 0) return; if (values.length == 0) return;
try { try {
final Class<T> clazz = (Class<T>) values[0].getClass();
final EntityInfo<T> info = loadEntityInfo(clazz);
final EntityCache<T> cache = info.getCache(); final EntityCache<T> cache = info.getCache();
if (!info.isVirtualEntity()) {
final String sql = info.insertSQL; final String sql = info.insertSQL;
if (debug.get()) logger.finest(clazz.getSimpleName() + " insert sql=" + sql); if (debug.get()) logger.finest(info.getType().getSimpleName() + " insert sql=" + sql);
final PreparedStatement prestmt = info.autoGenerated final PreparedStatement prestmt = info.autoGenerated
? conn.prepareStatement(sql, Statement.RETURN_GENERATED_KEYS) : conn.prepareStatement(sql); ? conn.prepareStatement(sql, Statement.RETURN_GENERATED_KEYS) : conn.prepareStatement(sql);
final Class primaryType = info.getPrimary().type(); final Class primaryType = info.getPrimary().type();
@@ -474,13 +482,14 @@ public final class DataJDBCSource implements DataSource {
} }
set.close(); set.close();
} }
prestmt.close();
}
if (cache != null) { if (cache != null) {
for (final T value : values) { for (final T value : values) {
cache.insert(value); cache.insert(value);
} }
if (cacheListener != null) cacheListener.insert(name, clazz, values); if (cacheListener != null) cacheListener.insert(name, info.getType(), values);
} }
prestmt.close();
} catch (SQLException e) { } catch (SQLException e) {
throw new RuntimeException(e); throw new RuntimeException(e);
} }
@@ -505,9 +514,15 @@ public final class DataJDBCSource implements DataSource {
*/ */
@Override @Override
public <T> void delete(T... values) { public <T> void delete(T... values) {
if (values.length == 0) return;
final EntityInfo<T> info = loadEntityInfo((Class<T>) values[0].getClass());
if (info.isVirtualEntity()) {
delete(null, info, values);
return;
}
Connection conn = createWriteSQLConnection(); Connection conn = createWriteSQLConnection();
try { try {
delete(conn, values); delete(conn, info, values);
} finally { } finally {
closeSQLConnection(conn); closeSQLConnection(conn);
} }
@@ -515,27 +530,32 @@ public final class DataJDBCSource implements DataSource {
@Override @Override
public <T> void delete(final DataConnection conn, T... values) { public <T> void delete(final DataConnection conn, T... values) {
delete((Connection) conn.getConnection(), values); if (values.length == 0) return;
final EntityInfo<T> info = loadEntityInfo((Class<T>) values[0].getClass());
delete((Connection) conn.getConnection(), info, values);
} }
private <T> void delete(final Connection conn, T... values) { private <T> void delete(final Connection conn, final EntityInfo<T> info, T... values) {
if (values.length == 0) return; if (values.length == 0) return;
final Class clazz = values[0].getClass();
final EntityInfo<T> info = loadEntityInfo(clazz);
final Attribute primary = info.getPrimary(); final Attribute primary = info.getPrimary();
Serializable[] ids = new Serializable[values.length]; Serializable[] ids = new Serializable[values.length];
int i = 0; int i = 0;
for (final T value : values) { for (final T value : values) {
ids[i++] = (Serializable) primary.get(value); ids[i++] = (Serializable) primary.get(value);
} }
delete(conn, clazz, ids); delete(conn, info, ids);
} }
@Override @Override
public <T> void delete(Class<T> clazz, Serializable... ids) { public <T> void delete(Class<T> clazz, Serializable... ids) {
final EntityInfo<T> info = loadEntityInfo(clazz);
if (info.isVirtualEntity()) {
delete(null, info, ids);
return;
}
Connection conn = createWriteSQLConnection(); Connection conn = createWriteSQLConnection();
try { try {
delete(conn, clazz, ids); delete(conn, info, ids);
} finally { } finally {
closeSQLConnection(conn); closeSQLConnection(conn);
} }
@@ -543,27 +563,28 @@ public final class DataJDBCSource implements DataSource {
@Override @Override
public <T> void delete(final DataConnection conn, Class<T> clazz, Serializable... ids) { public <T> void delete(final DataConnection conn, Class<T> clazz, Serializable... ids) {
delete((Connection) conn.getConnection(), clazz, ids); delete((Connection) conn.getConnection(), loadEntityInfo(clazz), ids);
} }
private <T> void delete(final Connection conn, Class<T> clazz, Serializable... keys) { private <T> void delete(final Connection conn, final EntityInfo<T> info, Serializable... keys) {
if (keys.length == 0) return; if (keys.length == 0) return;
try { try {
final EntityInfo<T> info = loadEntityInfo(clazz); if (!info.isVirtualEntity()) {
String sql = "DELETE FROM " + info.getTable() + " WHERE " + info.getPrimarySQLColumn() String sql = "DELETE FROM " + info.getTable() + " WHERE " + info.getPrimarySQLColumn()
+ " IN " + formatToString(keys); + " IN " + formatToString(keys);
if (debug.get()) logger.finest(clazz.getSimpleName() + " delete sql=" + sql); if (debug.get()) logger.finest(info.getType().getSimpleName() + " delete sql=" + sql);
final Statement stmt = conn.createStatement(); final Statement stmt = conn.createStatement();
stmt.execute(sql); stmt.execute(sql);
stmt.close(); stmt.close();
if (writeListener != null) writeListener.delete(name, sql); if (writeListener != null) writeListener.delete(name, sql);
}
//------------------------------------ //------------------------------------
final EntityCache<T> cache = info.getCache(); final EntityCache<T> cache = info.getCache();
if (cache == null) return; if (cache == null) return;
final Attribute<T, Serializable> attr = info.getPrimary(); final Attribute<T, Serializable> attr = info.getPrimary();
final Serializable[] keys2 = keys; final Serializable[] keys2 = keys;
Serializable[] ids = cache.delete((T t) -> Arrays.binarySearch(keys2, attr.get(t)) >= 0); Serializable[] ids = cache.delete((T t) -> Arrays.binarySearch(keys2, attr.get(t)) >= 0);
if (cacheListener != null) cacheListener.delete(name, clazz, ids); if (cacheListener != null) cacheListener.delete(name, info.getType(), ids);
} catch (SQLException e) { } catch (SQLException e) {
throw new RuntimeException(e); throw new RuntimeException(e);
} }
@@ -571,9 +592,14 @@ public final class DataJDBCSource implements DataSource {
@Override @Override
public <T> void delete(Class<T> clazz, FilterNode node) { public <T> void delete(Class<T> clazz, FilterNode node) {
final EntityInfo<T> info = loadEntityInfo(clazz);
if (info.isVirtualEntity()) {
delete(null, info, node);
return;
}
Connection conn = createWriteSQLConnection(); Connection conn = createWriteSQLConnection();
try { try {
delete(conn, clazz, node); delete(conn, info, node);
} finally { } finally {
closeSQLConnection(conn); closeSQLConnection(conn);
} }
@@ -581,23 +607,24 @@ public final class DataJDBCSource implements DataSource {
@Override @Override
public <T> void delete(final DataConnection conn, Class<T> clazz, FilterNode node) { public <T> void delete(final DataConnection conn, Class<T> clazz, FilterNode node) {
delete((Connection) conn.getConnection(), clazz, node); delete((Connection) conn.getConnection(), loadEntityInfo(clazz), node);
} }
private <T> void delete(final Connection conn, Class<T> clazz, FilterNode node) { private <T> void delete(final Connection conn, final EntityInfo<T> info, FilterNode node) {
try { try {
final EntityInfo<T> info = loadEntityInfo(clazz); if (!info.isVirtualEntity()) {
String sql = "DELETE FROM " + info.getTable() + " a" + node.createFilterSQLExpress(info, null); String sql = "DELETE FROM " + info.getTable() + " a" + node.createFilterSQLExpress(info, null);
if (debug.get()) logger.finest(clazz.getSimpleName() + " delete sql=" + sql); if (debug.get()) logger.finest(info.getType().getSimpleName() + " delete sql=" + sql);
final Statement stmt = conn.createStatement(); final Statement stmt = conn.createStatement();
stmt.execute(sql); stmt.execute(sql);
stmt.close(); stmt.close();
if (writeListener != null) writeListener.delete(name, sql); if (writeListener != null) writeListener.delete(name, sql);
}
//------------------------------------ //------------------------------------
final EntityCache<T> cache = info.getCache(); final EntityCache<T> cache = info.getCache();
if (cache == null) return; if (cache == null) return;
Serializable[] ids = cache.delete(node.createFilterPredicate(info, null)); Serializable[] ids = cache.delete(node.createFilterPredicate(info, null));
if (cacheListener != null) cacheListener.delete(name, clazz, ids); if (cacheListener != null) cacheListener.delete(name, info.getType(), ids);
} catch (SQLException e) { } catch (SQLException e) {
throw new RuntimeException(e); throw new RuntimeException(e);
} }
@@ -622,9 +649,15 @@ public final class DataJDBCSource implements DataSource {
*/ */
@Override @Override
public <T> void update(T... values) { public <T> void update(T... values) {
if (values.length == 0) return;
final EntityInfo<T> info = loadEntityInfo((Class<T>) values[0].getClass());
if (info.isVirtualEntity()) {
update(null, info, values);
return;
}
Connection conn = createWriteSQLConnection(); Connection conn = createWriteSQLConnection();
try { try {
update(conn, values); update(conn, info, values);
} finally { } finally {
closeSQLConnection(conn); closeSQLConnection(conn);
} }
@@ -632,13 +665,15 @@ public final class DataJDBCSource implements DataSource {
@Override @Override
public <T> void update(final DataConnection conn, T... values) { public <T> void update(final DataConnection conn, T... values) {
update((Connection) conn.getConnection(), values); if (values.length == 0) return;
final EntityInfo<T> info = loadEntityInfo((Class<T>) values[0].getClass());
update((Connection) conn.getConnection(), info, values);
} }
private <T> void update(final Connection conn, T... values) { private <T> void update(final Connection conn, final EntityInfo<T> info, T... values) {
try { try {
Class clazz = values[0].getClass(); Class clazz = info.getType();
final EntityInfo<T> info = loadEntityInfo(clazz); if (!info.isVirtualEntity()) {
if (debug.get()) logger.finest(clazz.getSimpleName() + " update sql=" + info.updateSQL); if (debug.get()) logger.finest(clazz.getSimpleName() + " update sql=" + info.updateSQL);
final Attribute<T, Serializable> primary = info.getPrimary(); final Attribute<T, Serializable> primary = info.getPrimary();
final PreparedStatement prestmt = conn.prepareStatement(info.updateSQL); final PreparedStatement prestmt = conn.prepareStatement(info.updateSQL);
@@ -683,6 +718,7 @@ public final class DataJDBCSource implements DataSource {
prestmt.executeBatch(); prestmt.executeBatch();
prestmt.close(); prestmt.close();
if (writeListener != null) writeListener.update(name, sqls); if (writeListener != null) writeListener.update(name, sqls);
}
//--------------------------------------------------- //---------------------------------------------------
final EntityCache<T> cache = info.getCache(); final EntityCache<T> cache = info.getCache();
if (cache == null) return; if (cache == null) return;
@@ -706,9 +742,14 @@ public final class DataJDBCSource implements DataSource {
*/ */
@Override @Override
public <T> void updateColumn(Class<T> clazz, Serializable id, String column, Serializable value) { public <T> void updateColumn(Class<T> clazz, Serializable id, String column, Serializable value) {
final EntityInfo<T> info = loadEntityInfo(clazz);
if (info.isVirtualEntity()) {
updateColumn(null, info, id, column, value);
return;
}
Connection conn = createWriteSQLConnection(); Connection conn = createWriteSQLConnection();
try { try {
updateColumn(conn, clazz, id, column, value); updateColumn(conn, info, id, column, value);
} finally { } finally {
closeSQLConnection(conn); closeSQLConnection(conn);
} }
@@ -716,24 +757,25 @@ public final class DataJDBCSource implements DataSource {
@Override @Override
public <T> void updateColumn(DataConnection conn, Class<T> clazz, Serializable id, String column, Serializable value) { public <T> void updateColumn(DataConnection conn, Class<T> clazz, Serializable id, String column, Serializable value) {
updateColumn((Connection) conn.getConnection(), clazz, id, column, value); updateColumn((Connection) conn.getConnection(), loadEntityInfo(clazz), id, column, value);
} }
private <T> void updateColumn(Connection conn, Class<T> clazz, Serializable id, String column, Serializable value) { private <T> void updateColumn(Connection conn, final EntityInfo<T> info, Serializable id, String column, Serializable value) {
try { try {
final EntityInfo<T> info = loadEntityInfo(clazz); if (!info.isVirtualEntity()) {
String sql = "UPDATE " + info.getTable() + " SET " + info.getSQLColumn(column) + " = " String sql = "UPDATE " + info.getTable() + " SET " + info.getSQLColumn(column) + " = "
+ formatToString(value) + " WHERE " + info.getPrimarySQLColumn() + " = " + formatToString(id); + formatToString(value) + " WHERE " + info.getPrimarySQLColumn() + " = " + formatToString(id);
if (debug.get()) logger.finest(clazz.getSimpleName() + " update sql=" + sql); if (debug.get()) logger.finest(info.getType().getSimpleName() + " update sql=" + sql);
final Statement stmt = conn.createStatement(); final Statement stmt = conn.createStatement();
stmt.execute(sql); stmt.execute(sql);
stmt.close(); stmt.close();
if (writeListener != null) writeListener.update(name, sql); if (writeListener != null) writeListener.update(name, sql);
}
//--------------------------------------------------- //---------------------------------------------------
final EntityCache<T> cache = info.getCache(); final EntityCache<T> cache = info.getCache();
if (cache == null) return; if (cache == null) return;
T rs = cache.update(id, (Attribute<T, Serializable>) info.getAttribute(column), value); T rs = cache.update(id, (Attribute<T, Serializable>) info.getAttribute(column), value);
if (cacheListener != null) cacheListener.update(name, clazz, rs); if (cacheListener != null) cacheListener.update(name, info.getType(), rs);
} catch (SQLException e) { } catch (SQLException e) {
throw new RuntimeException(e); throw new RuntimeException(e);
} finally { } finally {
@@ -752,9 +794,14 @@ public final class DataJDBCSource implements DataSource {
*/ */
@Override @Override
public <T> void updateColumnIncrement(Class<T> clazz, Serializable id, String column, long incvalue) { public <T> void updateColumnIncrement(Class<T> clazz, Serializable id, String column, long incvalue) {
final EntityInfo<T> info = loadEntityInfo(clazz);
if (info.isVirtualEntity()) {
updateColumnIncrement(null, info, id, column, incvalue);
return;
}
Connection conn = createWriteSQLConnection(); Connection conn = createWriteSQLConnection();
try { try {
updateColumnIncrement(conn, clazz, id, column, incvalue); updateColumnIncrement(conn, info, id, column, incvalue);
} finally { } finally {
closeSQLConnection(conn); closeSQLConnection(conn);
} }
@@ -762,26 +809,27 @@ public final class DataJDBCSource implements DataSource {
@Override @Override
public <T> void updateColumnIncrement(DataConnection conn, Class<T> clazz, Serializable id, String column, long incvalue) { public <T> void updateColumnIncrement(DataConnection conn, Class<T> clazz, Serializable id, String column, long incvalue) {
updateColumnIncrement((Connection) conn.getConnection(), clazz, id, column, incvalue); updateColumnIncrement((Connection) conn.getConnection(), loadEntityInfo(clazz), id, column, incvalue);
} }
private <T> void updateColumnIncrement(Connection conn, Class<T> clazz, Serializable id, String column, long incvalue) { private <T> void updateColumnIncrement(Connection conn, final EntityInfo<T> info, Serializable id, String column, long incvalue) {
try { try {
final EntityInfo<T> info = loadEntityInfo(clazz); if (!info.isVirtualEntity()) {
String col = info.getSQLColumn(column); String col = info.getSQLColumn(column);
String sql = "UPDATE " + info.getTable() + " SET " + col + " = " + col + " + (" + incvalue String sql = "UPDATE " + info.getTable() + " SET " + col + " = " + col + " + (" + incvalue
+ ") WHERE " + info.getPrimarySQLColumn() + " = " + formatToString(id); + ") WHERE " + info.getPrimarySQLColumn() + " = " + formatToString(id);
if (debug.get()) logger.finest(clazz.getSimpleName() + " update sql=" + sql); if (debug.get()) logger.finest(info.getType().getSimpleName() + " update sql=" + sql);
final Statement stmt = conn.createStatement(); final Statement stmt = conn.createStatement();
stmt.execute(sql); stmt.execute(sql);
stmt.close(); stmt.close();
if (writeListener != null) writeListener.update(name, sql); if (writeListener != null) writeListener.update(name, sql);
}
//--------------------------------------------------- //---------------------------------------------------
final EntityCache<T> cache = info.getCache(); final EntityCache<T> cache = info.getCache();
if (cache == null) return; if (cache == null) return;
Attribute<T, Serializable> attr = info.getAttribute(column); Attribute<T, Serializable> attr = info.getAttribute(column);
T value = cache.updateColumnIncrement(id, attr, incvalue); T value = cache.updateColumnIncrement(id, attr, incvalue);
if (value != null && cacheListener != null) cacheListener.update(name, clazz, value); if (value != null && cacheListener != null) cacheListener.update(name, info.getType(), value);
} catch (SQLException e) { } catch (SQLException e) {
throw new RuntimeException(e); throw new RuntimeException(e);
} finally { } finally {
@@ -798,9 +846,14 @@ public final class DataJDBCSource implements DataSource {
*/ */
@Override @Override
public <T> void updateColumns(final T value, final String... columns) { public <T> void updateColumns(final T value, final String... columns) {
final EntityInfo<T> info = loadEntityInfo((Class<T>) value.getClass());
if (info.isVirtualEntity()) {
updateColumns(null, info, value, columns);
return;
}
Connection conn = createWriteSQLConnection(); Connection conn = createWriteSQLConnection();
try { try {
updateColumns(conn, value, columns); updateColumns(conn, info, value, columns);
} finally { } finally {
closeSQLConnection(conn); closeSQLConnection(conn);
} }
@@ -808,24 +861,27 @@ public final class DataJDBCSource implements DataSource {
@Override @Override
public <T> void updateColumns(final DataConnection conn, final T value, final String... columns) { public <T> void updateColumns(final DataConnection conn, final T value, final String... columns) {
updateColumns((Connection) conn.getConnection(), value, columns); updateColumns((Connection) conn.getConnection(), loadEntityInfo((Class<T>) value.getClass()), value, columns);
} }
private <T> void updateColumns(final Connection conn, final T value, final String... columns) { private <T> void updateColumns(final Connection conn, final EntityInfo<T> info, final T value, final String... columns) {
if (value == null || columns.length < 1) return; if (value == null || columns.length < 1) return;
try { try {
final Class<T> clazz = (Class<T>) value.getClass(); final Class<T> clazz = (Class<T>) value.getClass();
final EntityInfo<T> info = loadEntityInfo(clazz);
StringBuilder setsql = new StringBuilder(); StringBuilder setsql = new StringBuilder();
final Serializable id = info.getPrimary().get(value); final Serializable id = info.getPrimary().get(value);
final List<Attribute<T, Serializable>> attrs = new ArrayList<>(); final List<Attribute<T, Serializable>> attrs = new ArrayList<>();
final boolean virtual = info.isVirtualEntity();
for (String col : columns) { for (String col : columns) {
Attribute<T, Serializable> attr = info.getUpdateAttribute(col); Attribute<T, Serializable> attr = info.getUpdateAttribute(col);
if (attr == null) continue; if (attr == null) continue;
attrs.add(attr);
if (!virtual) {
if (setsql.length() > 0) setsql.append(','); if (setsql.length() > 0) setsql.append(',');
setsql.append(info.getSQLColumn(col)).append(" = ").append(formatToString(attr.get(value))); setsql.append(info.getSQLColumn(col)).append(" = ").append(formatToString(attr.get(value)));
attrs.add(attr);
} }
}
if (!virtual) {
String sql = "UPDATE " + info.getTable() + " SET " + setsql String sql = "UPDATE " + info.getTable() + " SET " + setsql
+ " WHERE " + info.getPrimarySQLColumn() + " = " + formatToString(id); + " WHERE " + info.getPrimarySQLColumn() + " = " + formatToString(id);
if (debug.get()) logger.finest(value.getClass().getSimpleName() + ": " + sql); if (debug.get()) logger.finest(value.getClass().getSimpleName() + ": " + sql);
@@ -833,6 +889,7 @@ public final class DataJDBCSource implements DataSource {
stmt.execute(sql); stmt.execute(sql);
stmt.close(); stmt.close();
if (writeListener != null) writeListener.update(name, sql); if (writeListener != null) writeListener.update(name, sql);
}
//--------------------------------------------------- //---------------------------------------------------
final EntityCache<T> cache = info.getCache(); final EntityCache<T> cache = info.getCache();
if (cache == null) return; if (cache == null) return;
@@ -887,7 +944,7 @@ public final class DataJDBCSource implements DataSource {
final EntityInfo<T> info = loadEntityInfo(entityClass); final EntityInfo<T> info = loadEntityInfo(entityClass);
if (node == null && bean != null) node = loadFilterBeanNode(bean.getClass()); if (node == null && bean != null) node = loadFilterBeanNode(bean.getClass());
final EntityCache<T> cache = info.getCache(); final EntityCache<T> cache = info.getCache();
if (cache != null && cache.isFullLoaded()) { if (cache != null && (info.isVirtualEntity() || cache.isFullLoaded())) {
Predicate<T> filter = node == null ? null : node.createFilterPredicate(info, bean); Predicate<T> filter = node == null ? null : node.createFilterPredicate(info, bean);
if (node == null || node.isJoinAllCached()) { if (node == null || node.isJoinAllCached()) {
return cache.getNumberResult(reckon, column == null ? null : info.getAttribute(column), filter); return cache.getNumberResult(reckon, column == null ? null : info.getAttribute(column), filter);
@@ -934,7 +991,7 @@ public final class DataJDBCSource implements DataSource {
final EntityInfo info = loadEntityInfo(entityClass); final EntityInfo info = loadEntityInfo(entityClass);
if (node == null && bean != null) node = loadFilterBeanNode(bean.getClass()); if (node == null && bean != null) node = loadFilterBeanNode(bean.getClass());
final EntityCache cache = info.getCache(); final EntityCache cache = info.getCache();
if (cache != null && cache.isFullLoaded()) { if (cache != null && (info.isVirtualEntity() || cache.isFullLoaded())) {
Predicate filter = node == null ? null : node.createFilterPredicate(info, bean); Predicate filter = node == null ? null : node.createFilterPredicate(info, bean);
if (node == null || node.isJoinAllCached()) { if (node == null || node.isJoinAllCached()) {
return cache.getMapResult(info.getAttribute(keyColumn), reckon, reckonColumn == null ? null : info.getAttribute(reckonColumn), filter); return cache.getMapResult(info.getAttribute(keyColumn), reckon, reckonColumn == null ? null : info.getAttribute(reckonColumn), filter);
@@ -1049,6 +1106,7 @@ public final class DataJDBCSource implements DataSource {
/** /**
* 根据过滤对象FilterBean查询对象集合 * 根据过滤对象FilterBean查询对象集合
* *
* @param <K>
* @param <T> * @param <T>
* @param clazz * @param clazz
* @param bean * @param bean
@@ -1219,7 +1277,7 @@ public final class DataJDBCSource implements DataSource {
Predicate<T> filter = node == null ? null : node.createFilterPredicate(info, bean); Predicate<T> filter = node == null ? null : node.createFilterPredicate(info, bean);
if (node == null || node.isJoinAllCached()) { if (node == null || node.isJoinAllCached()) {
Sheet<T> sheet = cache.querySheet(selects, filter, flipper, FilterNode.createFilterComparator(info, flipper)); Sheet<T> sheet = cache.querySheet(selects, filter, flipper, FilterNode.createFilterComparator(info, flipper));
if (!sheet.isEmpty() || cache.isFullLoaded()) return sheet; if (!sheet.isEmpty() || info.isVirtualEntity() || cache.isFullLoaded()) return sheet;
} }
} }
final Connection conn = createReadSQLConnection(); final Connection conn = createReadSQLConnection();

View File

@@ -31,7 +31,7 @@ public abstract class DataSourceFactory {
// } // }
// if (jpa) return new DataJPASource(unitName); // if (jpa) return new DataJPASource(unitName);
try { try {
return new DataJDBCSource(unitName); return new DataDefaultSource(unitName);
} catch (IOException ex) { } catch (IOException ex) {
logger.log(Level.WARNING, "cannot create DataSource (" + unitName + ")", ex); logger.log(Level.WARNING, "cannot create DataSource (" + unitName + ")", ex);
return null; return null;

View File

@@ -34,7 +34,7 @@ public final class EntityInfo<T> {
//Entity类的类名 //Entity类的类名
private final Class<T> type; private final Class<T> type;
//类对应的数据表名 //类对应的数据表名, 如果是VirtualEntity 类, 则该字段为null
private final String table; private final String table;
private final Creator<T> creator; private final Creator<T> creator;
@@ -115,7 +115,11 @@ public final class EntityInfo<T> {
this.logLevel = ll == null ? Integer.MIN_VALUE : Level.parse(ll.value()).intValue(); this.logLevel = ll == null ? Integer.MIN_VALUE : Level.parse(ll.value()).intValue();
//--------------------------------------------- //---------------------------------------------
Table t = type.getAnnotation(Table.class); Table t = type.getAnnotation(Table.class);
if (type.getAnnotation(VirtualEntity.class) != null) {
this.table = null;
} else {
this.table = (t == null) ? type.getSimpleName().toLowerCase() : (t.catalog().isEmpty()) ? t.name() : (t.catalog() + '.' + t.name()); this.table = (t == null) ? type.getSimpleName().toLowerCase() : (t.catalog().isEmpty()) ? t.name() : (t.catalog() + '.' + t.name());
}
this.creator = Creator.create(type); this.creator = Creator.create(type);
Attribute idAttr0 = null; Attribute idAttr0 = null;
Map<String, String> aliasmap0 = null; Map<String, String> aliasmap0 = null;
@@ -186,10 +190,10 @@ public final class EntityInfo<T> {
} while ((cltmp = cltmp.getSuperclass()) != Object.class); } while ((cltmp = cltmp.getSuperclass()) != Object.class);
this.primary = idAttr0; this.primary = idAttr0;
this.aliasmap = aliasmap0; this.aliasmap = aliasmap0;
{
this.queryAttributes = queryattrs.toArray(new Attribute[queryattrs.size()]); this.queryAttributes = queryattrs.toArray(new Attribute[queryattrs.size()]);
this.insertAttributes = insertattrs.toArray(new Attribute[insertattrs.size()]); this.insertAttributes = insertattrs.toArray(new Attribute[insertattrs.size()]);
this.updateAttributes = updateattrs.toArray(new Attribute[updateattrs.size()]); this.updateAttributes = updateattrs.toArray(new Attribute[updateattrs.size()]);
if (table != null) {
StringBuilder insertsb = new StringBuilder(); StringBuilder insertsb = new StringBuilder();
StringBuilder insertsb2 = new StringBuilder(); StringBuilder insertsb2 = new StringBuilder();
for (String col : insertcols) { for (String col : insertcols) {
@@ -207,13 +211,18 @@ public final class EntityInfo<T> {
this.updateSQL = "UPDATE " + table + " SET " + updatesb + " WHERE " + getPrimarySQLColumn() + " = ?"; this.updateSQL = "UPDATE " + table + " SET " + updatesb + " WHERE " + getPrimarySQLColumn() + " = ?";
this.deleteSQL = "DELETE FROM " + table + " WHERE " + getPrimarySQLColumn() + " = ?"; this.deleteSQL = "DELETE FROM " + table + " WHERE " + getPrimarySQLColumn() + " = ?";
this.querySQL = "SELECT * FROM " + table + " WHERE " + getPrimarySQLColumn() + " = ?"; this.querySQL = "SELECT * FROM " + table + " WHERE " + getPrimarySQLColumn() + " = ?";
} else {
this.insertSQL = null;
this.updateSQL = null;
this.deleteSQL = null;
this.querySQL = null;
} }
this.autoGenerated = auto; this.autoGenerated = auto;
this.distributed = sqldistribute; this.distributed = sqldistribute;
this.allocationSize = allocationSize0; this.allocationSize = allocationSize0;
//----------------cache-------------- //----------------cache--------------
Cacheable c = type.getAnnotation(Cacheable.class); Cacheable c = type.getAnnotation(Cacheable.class);
if (!cacheForbidden && c != null && c.value()) { if (this.table == null || (!cacheForbidden && c != null && c.value())) {
this.cache = new EntityCache<>(type, creator, primary, attributes); this.cache = new EntityCache<>(type, creator, primary, attributes);
} else { } else {
this.cache = null; this.cache = null;
@@ -241,6 +250,15 @@ public final class EntityInfo<T> {
return type; return type;
} }
/**
* 是否虚拟类
* <p>
* @return
*/
public boolean isVirtualEntity() {
return table == null;
}
public String getTable() { public String getTable() {
return table; return table;
} }

View File

@@ -5,7 +5,7 @@
*/ */
package com.wentch.redkale.source; package com.wentch.redkale.source;
import static com.wentch.redkale.source.DataJDBCSource.*; import static com.wentch.redkale.source.DataDefaultSource.*;
import java.io.*; import java.io.*;
import java.lang.ref.WeakReference; import java.lang.ref.WeakReference;
import java.lang.reflect.Method; import java.lang.reflect.Method;
@@ -40,7 +40,7 @@ public class JDBCPoolSource {
private final ConnectionEventListener listener; private final ConnectionEventListener listener;
private final DataJDBCSource dataSource; private final DataDefaultSource dataSource;
private final String stype; // "" 或 "read" 或 "write" private final String stype; // "" 或 "read" 或 "write"
@@ -52,7 +52,7 @@ public class JDBCPoolSource {
private String password; private String password;
public JDBCPoolSource(DataJDBCSource source, String stype, Properties prop) { public JDBCPoolSource(DataDefaultSource source, String stype, Properties prop) {
this.dataSource = source; this.dataSource = source;
this.stype = stype; this.stype = stype;
this.source = createDataSource(prop); this.source = createDataSource(prop);

View File

@@ -0,0 +1,21 @@
/*
* To change this license header, choose License Headers in Project Properties.
* To change this template file, choose Tools | Templates
* and open the template in the editor.
*/
package com.wentch.redkale.source;
import java.lang.annotation.*;
import static java.lang.annotation.ElementType.TYPE;
import static java.lang.annotation.RetentionPolicy.RUNTIME;
/**
*
* @author zhangjx
*/
@Documented
@Target(TYPE)
@Retention(RUNTIME)
public @interface VirtualEntity {
}