Repository: incubator-ignite Updated Branches: refs/heads/ignite-63 9520f006c -> 531d9ba3f
http://git-wip-us.apache.org/repos/asf/incubator-ignite/blob/531d9ba3/modules/core/src/main/java/org/apache/ignite/jdbc/IgniteJdbcStatement.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/jdbc/IgniteJdbcStatement.java b/modules/core/src/main/java/org/apache/ignite/jdbc/IgniteJdbcStatement.java new file mode 100644 index 0000000..027768d --- /dev/null +++ b/modules/core/src/main/java/org/apache/ignite/jdbc/IgniteJdbcStatement.java @@ -0,0 +1,449 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You 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 org.apache.ignite.jdbc; + +import org.apache.ignite.client.*; +import org.apache.ignite.internal.util.typedef.internal.*; +import org.apache.ignite.jdbc.typedef.*; + +import java.sql.*; +import java.util.*; + +import static java.sql.ResultSet.*; + +/** + * JDBC statement implementation. + */ +class IgniteJdbcStatement implements Statement { + /** Task name. */ + private static final String TASK_NAME = + "org.apache.ignite.internal.processors.cache.query.jdbc.GridCacheQueryJdbcTask"; + + /** Default fetch size. */ + private static final int DFLT_FETCH_SIZE = 1024; + + /** Connection. */ + private final IgniteJdbcConnection conn; + + /** Closed flag. */ + private boolean closed; + + /** Rows limit. */ + private int maxRows; + + /** Query timeout. */ + private int timeout; + + /** Current result set. */ + private ResultSet rs; + + /** Query arguments. */ + protected Object[] args; + + /** Fetch size. */ + private int fetchSize = DFLT_FETCH_SIZE; + + /** + * Creates new statement. + * + * @param conn Connection. + */ + IgniteJdbcStatement(IgniteJdbcConnection conn) { + assert conn != null; + + this.conn = conn; + } + + /** {@inheritDoc} */ + @Override public ResultSet executeQuery(String sql) throws SQLException { + ensureNotClosed(); + + rs = null; + + if (sql == null || sql.isEmpty()) + throw new SQLException("SQL query is empty"); + + try { + byte[] packet = conn.client().compute().execute(TASK_NAME, + JU.marshalArgument(JU.taskArgument(conn.nodeId(), conn.cacheName(), sql, timeout, args, fetchSize, + maxRows))); + + byte status = packet[0]; + byte[] data = new byte[packet.length - 1]; + + U.arrayCopy(packet, 1, data, 0, data.length); + + if (status == 1) + throw JU.unmarshalError(data); + else { + List<?> msg = JU.unmarshal(data); + + assert msg.size() == 7; + + UUID nodeId = (UUID)msg.get(0); + UUID futId = (UUID)msg.get(1); + List<String> tbls = (List<String>)msg.get(2); + List<String> cols = (List<String>)msg.get(3); + List<String> types = (List<String>)msg.get(4); + Collection<List<Object>> fields = (Collection<List<Object>>)msg.get(5); + boolean finished = (Boolean)msg.get(6); + + return new IgniteJdbcResultSet(this, nodeId, futId, tbls, cols, types, fields, finished, fetchSize); + } + } + catch (GridClientException e) { + throw new SQLException("Failed to query GridGain.", e); + } + } + + /** {@inheritDoc} */ + @Override public int executeUpdate(String sql) throws SQLException { + ensureNotClosed(); + + throw new SQLFeatureNotSupportedException("Updates are not supported."); + } + + /** {@inheritDoc} */ + @Override public void close() throws SQLException { + closed = true; + } + + /** {@inheritDoc} */ + @Override public int getMaxFieldSize() throws SQLException { + ensureNotClosed(); + + return 0; + } + + /** {@inheritDoc} */ + @Override public void setMaxFieldSize(int max) throws SQLException { + ensureNotClosed(); + + throw new SQLFeatureNotSupportedException("Field size limitation is not supported."); + } + + /** {@inheritDoc} */ + @Override public int getMaxRows() throws SQLException { + ensureNotClosed(); + + return maxRows; + } + + /** {@inheritDoc} */ + @Override public void setMaxRows(int maxRows) throws SQLException { + ensureNotClosed(); + + this.maxRows = maxRows; + } + + /** {@inheritDoc} */ + @Override public void setEscapeProcessing(boolean enable) throws SQLException { + ensureNotClosed(); + } + + /** {@inheritDoc} */ + @Override public int getQueryTimeout() throws SQLException { + ensureNotClosed(); + + return timeout; + } + + /** {@inheritDoc} */ + @Override public void setQueryTimeout(int timeout) throws SQLException { + ensureNotClosed(); + + this.timeout = timeout * 1000; + } + + /** {@inheritDoc} */ + @Override public void cancel() throws SQLException { + ensureNotClosed(); + + throw new SQLFeatureNotSupportedException("Cancellation is not supported."); + } + + /** {@inheritDoc} */ + @Override public SQLWarning getWarnings() throws SQLException { + ensureNotClosed(); + + return null; + } + + /** {@inheritDoc} */ + @Override public void clearWarnings() throws SQLException { + ensureNotClosed(); + } + + /** {@inheritDoc} */ + @Override public void setCursorName(String name) throws SQLException { + ensureNotClosed(); + + throw new SQLFeatureNotSupportedException("Updates are not supported."); + } + + /** {@inheritDoc} */ + @Override public boolean execute(String sql) throws SQLException { + ensureNotClosed(); + + rs = executeQuery(sql); + + return true; + } + + /** {@inheritDoc} */ + @Override public ResultSet getResultSet() throws SQLException { + ensureNotClosed(); + + ResultSet rs0 = rs; + + rs = null; + + return rs0; + } + + /** {@inheritDoc} */ + @Override public int getUpdateCount() throws SQLException { + ensureNotClosed(); + + return -1; + } + + /** {@inheritDoc} */ + @Override public boolean getMoreResults() throws SQLException { + ensureNotClosed(); + + throw new SQLFeatureNotSupportedException("Multiple open results are not supported."); + } + + /** {@inheritDoc} */ + @Override public void setFetchDirection(int direction) throws SQLException { + ensureNotClosed(); + + if (direction != FETCH_FORWARD) + throw new SQLFeatureNotSupportedException("Only forward direction is supported"); + } + + /** {@inheritDoc} */ + @Override public int getFetchDirection() throws SQLException { + ensureNotClosed(); + + return FETCH_FORWARD; + } + + /** {@inheritDoc} */ + @Override public void setFetchSize(int fetchSize) throws SQLException { + ensureNotClosed(); + + if (fetchSize <= 0) + throw new SQLException("Fetch size must be greater than zero."); + + this.fetchSize = fetchSize; + } + + /** {@inheritDoc} */ + @Override public int getFetchSize() throws SQLException { + ensureNotClosed(); + + return fetchSize; + } + + /** {@inheritDoc} */ + @Override public int getResultSetConcurrency() throws SQLException { + ensureNotClosed(); + + return CONCUR_READ_ONLY; + } + + /** {@inheritDoc} */ + @Override public int getResultSetType() throws SQLException { + ensureNotClosed(); + + return TYPE_FORWARD_ONLY; + } + + /** {@inheritDoc} */ + @Override public void addBatch(String sql) throws SQLException { + ensureNotClosed(); + + throw new SQLFeatureNotSupportedException("Updates are not supported."); + } + + /** {@inheritDoc} */ + @Override public void clearBatch() throws SQLException { + ensureNotClosed(); + + throw new SQLFeatureNotSupportedException("Updates are not supported."); + } + + /** {@inheritDoc} */ + @Override public int[] executeBatch() throws SQLException { + ensureNotClosed(); + + throw new SQLFeatureNotSupportedException("Updates are not supported."); + } + + /** {@inheritDoc} */ + @Override public Connection getConnection() throws SQLException { + ensureNotClosed(); + + return conn; + } + + /** {@inheritDoc} */ + @Override public boolean getMoreResults(int curr) throws SQLException { + ensureNotClosed(); + + throw new SQLFeatureNotSupportedException("Multiple open results are not supported."); + } + + /** {@inheritDoc} */ + @Override public ResultSet getGeneratedKeys() throws SQLException { + ensureNotClosed(); + + throw new SQLFeatureNotSupportedException("Updates are not supported."); + } + + /** {@inheritDoc} */ + @Override public int executeUpdate(String sql, int autoGeneratedKeys) throws SQLException { + ensureNotClosed(); + + throw new SQLFeatureNotSupportedException("Updates are not supported."); + } + + /** {@inheritDoc} */ + @Override public int executeUpdate(String sql, int[] colIndexes) throws SQLException { + ensureNotClosed(); + + throw new SQLFeatureNotSupportedException("Updates are not supported."); + } + + /** {@inheritDoc} */ + @Override public int executeUpdate(String sql, String[] colNames) throws SQLException { + ensureNotClosed(); + + throw new SQLFeatureNotSupportedException("Updates are not supported."); + } + + /** {@inheritDoc} */ + @Override public boolean execute(String sql, int autoGeneratedKeys) throws SQLException { + ensureNotClosed(); + + if (autoGeneratedKeys == RETURN_GENERATED_KEYS) + throw new SQLFeatureNotSupportedException("Updates are not supported."); + + return execute(sql); + } + + /** {@inheritDoc} */ + @Override public boolean execute(String sql, int[] colIndexes) throws SQLException { + ensureNotClosed(); + + if (colIndexes != null && colIndexes.length > 0) + throw new SQLFeatureNotSupportedException("Updates are not supported."); + + return execute(sql); + } + + /** {@inheritDoc} */ + @Override public boolean execute(String sql, String[] colNames) throws SQLException { + ensureNotClosed(); + + if (colNames != null && colNames.length > 0) + throw new SQLFeatureNotSupportedException("Updates are not supported."); + + return execute(sql); + } + + /** {@inheritDoc} */ + @Override public int getResultSetHoldability() throws SQLException { + ensureNotClosed(); + + return HOLD_CURSORS_OVER_COMMIT; + } + + /** {@inheritDoc} */ + @Override public boolean isClosed() throws SQLException { + return closed; + } + + /** {@inheritDoc} */ + @Override public void setPoolable(boolean poolable) throws SQLException { + ensureNotClosed(); + + if (poolable) + throw new SQLFeatureNotSupportedException("Pooling is not supported."); + } + + /** {@inheritDoc} */ + @Override public boolean isPoolable() throws SQLException { + ensureNotClosed(); + + return false; + } + + /** {@inheritDoc} */ + @Override public <T> T unwrap(Class<T> iface) throws SQLException { + if (!isWrapperFor(iface)) + throw new SQLException("Statement is not a wrapper for " + iface.getName()); + + return (T)this; + } + + /** {@inheritDoc} */ + @Override public boolean isWrapperFor(Class<?> iface) throws SQLException { + return iface != null && iface == Statement.class; + } + + /** {@inheritDoc} */ + @Override public void closeOnCompletion() throws SQLException { + throw new SQLFeatureNotSupportedException("closeOnCompletion is not supported."); + } + + /** {@inheritDoc} */ + @Override public boolean isCloseOnCompletion() throws SQLException { + ensureNotClosed(); + + return false; + } + + /** + * Sets timeout in milliseconds. + * + * @param timeout Timeout. + */ + void timeout(int timeout) { + this.timeout = timeout; + } + + /** + * @return Connection. + */ + IgniteJdbcConnection connection() { + return conn; + } + + /** + * Ensures that statement is not closed. + * + * @throws SQLException If statement is closed. + */ + protected void ensureNotClosed() throws SQLException { + if (closed) + throw new SQLException("Statement is closed."); + } +} http://git-wip-us.apache.org/repos/asf/incubator-ignite/blob/531d9ba3/modules/core/src/main/java/org/apache/ignite/jdbc/typedef/JU.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/jdbc/typedef/JU.java b/modules/core/src/main/java/org/apache/ignite/jdbc/typedef/JU.java index bf13344..7ba3eb6 100644 --- a/modules/core/src/main/java/org/apache/ignite/jdbc/typedef/JU.java +++ b/modules/core/src/main/java/org/apache/ignite/jdbc/typedef/JU.java @@ -20,9 +20,9 @@ package org.apache.ignite.jdbc.typedef; import org.apache.ignite.jdbc.util.*; /** - * Defines internal {@code typedef} for {@link GridJdbcUtils}. + * Defines internal {@code typedef} for {@link org.apache.ignite.jdbc.util.IgniteJdbcUtils}. */ @SuppressWarnings("ExtendsUtilityClass") -public class JU extends GridJdbcUtils { +public class JU extends IgniteJdbcUtils { // No-op } http://git-wip-us.apache.org/repos/asf/incubator-ignite/blob/531d9ba3/modules/core/src/main/java/org/apache/ignite/jdbc/util/GridJdbcUtils.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/jdbc/util/GridJdbcUtils.java b/modules/core/src/main/java/org/apache/ignite/jdbc/util/GridJdbcUtils.java deleted file mode 100644 index 32c1aee..0000000 --- a/modules/core/src/main/java/org/apache/ignite/jdbc/util/GridJdbcUtils.java +++ /dev/null @@ -1,232 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You 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 org.apache.ignite.jdbc.util; - -import org.apache.ignite.*; -import org.apache.ignite.marshaller.*; -import org.apache.ignite.marshaller.jdk.*; -import org.apache.ignite.internal.util.typedef.internal.*; - -import java.sql.*; -import java.util.*; -import java.util.Date; - -import static java.sql.Types.*; - -/** - * Utility methods for JDBC driver. - */ -public class GridJdbcUtils { - /** Marshaller. */ - private static final IgniteMarshaller MARSHALLER = new IgniteJdkMarshaller(); - - /** - * Marshals task argument to byte array. - * - * @param args Task argument. - * @return Byte array. - * @throws SQLException In marshalling failed. - */ - public static byte[] marshalArgument(Map<String, Object> args) throws SQLException { - assert args != null; - - try { - return MARSHALLER.marshal(args); - } - catch (IgniteCheckedException e) { - throw new SQLException("Failed to unmarshal result.", e); - } - } - - /** - * Unmarshals exception from byte array. - * - * @param bytes Byte array. - * @return Exception. - * @throws SQLException If unmarshalling failed. - */ - public static SQLException unmarshalError(byte[] bytes) throws SQLException { - return unmarshal(bytes); - } - - /** - * Unmarshals object from byte array. - * - * @param bytes Byte array. - * @return Object. - * @throws SQLException If unmarshalling failed. - */ - public static <T> T unmarshal(byte[] bytes) throws SQLException { - assert bytes != null; - - try { - return MARSHALLER.unmarshal(bytes, null); - } - catch (IgniteCheckedException e) { - throw new SQLException("Failed to unmarshal result.", e); - } - } - - /** - * Creates task argument for first execution. - * - * @param nodeId Node ID. - * @param cacheName Cache name. - * @param sql SQL query. - * @param timeout Query timeout. - * @param args Query arguments. - * @param pageSize Page size. - * @param maxRows Maximum number of rows. - * @return Task argument. - */ - public static Map<String, Object> taskArgument(UUID nodeId, String cacheName, String sql, - long timeout, Object[] args, int pageSize, int maxRows) { - assert sql != null; - assert timeout >= 0; - assert pageSize > 0; - assert maxRows >= 0; - - Map<String, Object> map = U.newHashMap(7); - - map.put("confNodeId", nodeId); - map.put("cache", cacheName); - map.put("sql", sql); - map.put("timeout", timeout); - map.put("args", args != null ? Arrays.asList(args) : Collections.emptyList()); - map.put("pageSize", pageSize); - map.put("maxRows", maxRows); - - return map; - } - - /** - * Creates task argument. - * - * @param nodeId Node ID. - * @param futId Future ID. - * @param pageSize Page size. - * @param maxRows Maximum number of rows. - * @return Task argument. - */ - public static Map<String, Object> taskArgument(UUID nodeId, UUID futId, int pageSize, int maxRows) { - assert nodeId != null; - assert futId != null; - assert pageSize > 0; - assert maxRows >= 0; - - Map<String, Object> map = U.newHashMap(4); - - map.put("nodeId", nodeId); - map.put("futId", futId); - map.put("pageSize", pageSize); - map.put("maxRows", maxRows); - - return map; - } - - /** - * Converts Java class name to type from {@link Types}. - * - * @param cls Java class name. - * @return Type from {@link Types}. - */ - @SuppressWarnings("IfMayBeConditional") - public static int type(String cls) { - if (Boolean.class.getName().equals(cls) || boolean.class.getName().equals(cls)) - return BOOLEAN; - else if (Byte.class.getName().equals(cls) || byte.class.getName().equals(cls)) - return TINYINT; - else if (Short.class.getName().equals(cls) || short.class.getName().equals(cls)) - return SMALLINT; - else if (Integer.class.getName().equals(cls) || int.class.getName().equals(cls)) - return INTEGER; - else if (Long.class.getName().equals(cls) || long.class.getName().equals(cls)) - return BIGINT; - else if (Float.class.getName().equals(cls) || float.class.getName().equals(cls)) - return FLOAT; - else if (Double.class.getName().equals(cls) || double.class.getName().equals(cls)) - return DOUBLE; - else if (String.class.getName().equals(cls)) - return VARCHAR; - else if (byte[].class.getName().equals(cls)) - return BINARY; - else if (Time.class.getName().equals(cls)) - return TIME; - else if (Timestamp.class.getName().equals(cls)) - return TIMESTAMP; - else if (Date.class.getName().equals(cls)) - return DATE; - else - return OTHER; - } - - /** - * Converts Java class name to SQL type name. - * - * @param cls Java class name. - * @return SQL type name. - */ - @SuppressWarnings("IfMayBeConditional") - public static String typeName(String cls) { - if (Boolean.class.getName().equals(cls) || boolean.class.getName().equals(cls)) - return "BOOLEAN"; - else if (Byte.class.getName().equals(cls) || byte.class.getName().equals(cls)) - return "TINYINT"; - else if (Short.class.getName().equals(cls) || short.class.getName().equals(cls)) - return "SMALLINT"; - else if (Integer.class.getName().equals(cls) || int.class.getName().equals(cls)) - return "INTEGER"; - else if (Long.class.getName().equals(cls) || long.class.getName().equals(cls)) - return "BIGINT"; - else if (Float.class.getName().equals(cls) || float.class.getName().equals(cls)) - return "FLOAT"; - else if (Double.class.getName().equals(cls) || double.class.getName().equals(cls)) - return "DOUBLE"; - else if (String.class.getName().equals(cls)) - return "VARCHAR"; - else if (byte[].class.getName().equals(cls)) - return "BINARY"; - else if (Time.class.getName().equals(cls)) - return "TIME"; - else if (Timestamp.class.getName().equals(cls)) - return "TIMESTAMP"; - else if (Date.class.getName().equals(cls)) - return "DATE"; - else - return "OTHER"; - } - - /** - * Determines whether type is nullable. - * - * @param name Column name. - * @param cls Java class name. - * @return {@code True} if nullable. - */ - public static boolean nullable(String name, String cls) { - return !"_KEY".equalsIgnoreCase(name) && - !"_VAL".equalsIgnoreCase(name) && - !(boolean.class.getName().equals(cls) || - byte.class.getName().equals(cls) || - short.class.getName().equals(cls) || - int.class.getName().equals(cls) || - long.class.getName().equals(cls) || - float.class.getName().equals(cls) || - double.class.getName().equals(cls)); - } -} http://git-wip-us.apache.org/repos/asf/incubator-ignite/blob/531d9ba3/modules/core/src/main/java/org/apache/ignite/jdbc/util/IgniteJdbcUtils.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/jdbc/util/IgniteJdbcUtils.java b/modules/core/src/main/java/org/apache/ignite/jdbc/util/IgniteJdbcUtils.java new file mode 100644 index 0000000..b9875b0 --- /dev/null +++ b/modules/core/src/main/java/org/apache/ignite/jdbc/util/IgniteJdbcUtils.java @@ -0,0 +1,232 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You 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 org.apache.ignite.jdbc.util; + +import org.apache.ignite.*; +import org.apache.ignite.marshaller.*; +import org.apache.ignite.marshaller.jdk.*; +import org.apache.ignite.internal.util.typedef.internal.*; + +import java.sql.*; +import java.util.*; +import java.util.Date; + +import static java.sql.Types.*; + +/** + * Utility methods for JDBC driver. + */ +public class IgniteJdbcUtils { + /** Marshaller. */ + private static final IgniteMarshaller MARSHALLER = new IgniteJdkMarshaller(); + + /** + * Marshals task argument to byte array. + * + * @param args Task argument. + * @return Byte array. + * @throws SQLException In marshalling failed. + */ + public static byte[] marshalArgument(Map<String, Object> args) throws SQLException { + assert args != null; + + try { + return MARSHALLER.marshal(args); + } + catch (IgniteCheckedException e) { + throw new SQLException("Failed to unmarshal result.", e); + } + } + + /** + * Unmarshals exception from byte array. + * + * @param bytes Byte array. + * @return Exception. + * @throws SQLException If unmarshalling failed. + */ + public static SQLException unmarshalError(byte[] bytes) throws SQLException { + return unmarshal(bytes); + } + + /** + * Unmarshals object from byte array. + * + * @param bytes Byte array. + * @return Object. + * @throws SQLException If unmarshalling failed. + */ + public static <T> T unmarshal(byte[] bytes) throws SQLException { + assert bytes != null; + + try { + return MARSHALLER.unmarshal(bytes, null); + } + catch (IgniteCheckedException e) { + throw new SQLException("Failed to unmarshal result.", e); + } + } + + /** + * Creates task argument for first execution. + * + * @param nodeId Node ID. + * @param cacheName Cache name. + * @param sql SQL query. + * @param timeout Query timeout. + * @param args Query arguments. + * @param pageSize Page size. + * @param maxRows Maximum number of rows. + * @return Task argument. + */ + public static Map<String, Object> taskArgument(UUID nodeId, String cacheName, String sql, + long timeout, Object[] args, int pageSize, int maxRows) { + assert sql != null; + assert timeout >= 0; + assert pageSize > 0; + assert maxRows >= 0; + + Map<String, Object> map = U.newHashMap(7); + + map.put("confNodeId", nodeId); + map.put("cache", cacheName); + map.put("sql", sql); + map.put("timeout", timeout); + map.put("args", args != null ? Arrays.asList(args) : Collections.emptyList()); + map.put("pageSize", pageSize); + map.put("maxRows", maxRows); + + return map; + } + + /** + * Creates task argument. + * + * @param nodeId Node ID. + * @param futId Future ID. + * @param pageSize Page size. + * @param maxRows Maximum number of rows. + * @return Task argument. + */ + public static Map<String, Object> taskArgument(UUID nodeId, UUID futId, int pageSize, int maxRows) { + assert nodeId != null; + assert futId != null; + assert pageSize > 0; + assert maxRows >= 0; + + Map<String, Object> map = U.newHashMap(4); + + map.put("nodeId", nodeId); + map.put("futId", futId); + map.put("pageSize", pageSize); + map.put("maxRows", maxRows); + + return map; + } + + /** + * Converts Java class name to type from {@link Types}. + * + * @param cls Java class name. + * @return Type from {@link Types}. + */ + @SuppressWarnings("IfMayBeConditional") + public static int type(String cls) { + if (Boolean.class.getName().equals(cls) || boolean.class.getName().equals(cls)) + return BOOLEAN; + else if (Byte.class.getName().equals(cls) || byte.class.getName().equals(cls)) + return TINYINT; + else if (Short.class.getName().equals(cls) || short.class.getName().equals(cls)) + return SMALLINT; + else if (Integer.class.getName().equals(cls) || int.class.getName().equals(cls)) + return INTEGER; + else if (Long.class.getName().equals(cls) || long.class.getName().equals(cls)) + return BIGINT; + else if (Float.class.getName().equals(cls) || float.class.getName().equals(cls)) + return FLOAT; + else if (Double.class.getName().equals(cls) || double.class.getName().equals(cls)) + return DOUBLE; + else if (String.class.getName().equals(cls)) + return VARCHAR; + else if (byte[].class.getName().equals(cls)) + return BINARY; + else if (Time.class.getName().equals(cls)) + return TIME; + else if (Timestamp.class.getName().equals(cls)) + return TIMESTAMP; + else if (Date.class.getName().equals(cls)) + return DATE; + else + return OTHER; + } + + /** + * Converts Java class name to SQL type name. + * + * @param cls Java class name. + * @return SQL type name. + */ + @SuppressWarnings("IfMayBeConditional") + public static String typeName(String cls) { + if (Boolean.class.getName().equals(cls) || boolean.class.getName().equals(cls)) + return "BOOLEAN"; + else if (Byte.class.getName().equals(cls) || byte.class.getName().equals(cls)) + return "TINYINT"; + else if (Short.class.getName().equals(cls) || short.class.getName().equals(cls)) + return "SMALLINT"; + else if (Integer.class.getName().equals(cls) || int.class.getName().equals(cls)) + return "INTEGER"; + else if (Long.class.getName().equals(cls) || long.class.getName().equals(cls)) + return "BIGINT"; + else if (Float.class.getName().equals(cls) || float.class.getName().equals(cls)) + return "FLOAT"; + else if (Double.class.getName().equals(cls) || double.class.getName().equals(cls)) + return "DOUBLE"; + else if (String.class.getName().equals(cls)) + return "VARCHAR"; + else if (byte[].class.getName().equals(cls)) + return "BINARY"; + else if (Time.class.getName().equals(cls)) + return "TIME"; + else if (Timestamp.class.getName().equals(cls)) + return "TIMESTAMP"; + else if (Date.class.getName().equals(cls)) + return "DATE"; + else + return "OTHER"; + } + + /** + * Determines whether type is nullable. + * + * @param name Column name. + * @param cls Java class name. + * @return {@code True} if nullable. + */ + public static boolean nullable(String name, String cls) { + return !"_KEY".equalsIgnoreCase(name) && + !"_VAL".equalsIgnoreCase(name) && + !(boolean.class.getName().equals(cls) || + byte.class.getName().equals(cls) || + short.class.getName().equals(cls) || + int.class.getName().equals(cls) || + long.class.getName().equals(cls) || + float.class.getName().equals(cls) || + double.class.getName().equals(cls)); + } +}