List:Internals« Previous MessageNext Message »
From:mmatthews Date:September 7 2005 7:12pm
Subject:Connector/J commit: r4216 - in branches/branch_5_0/connector-j/src: com/mysql/jdbc testsuite/simple
View as plain text  
Modified:
   branches/branch_5_0/connector-j/src/com/mysql/jdbc/Connection.java
   branches/branch_5_0/connector-j/src/com/mysql/jdbc/EscapeProcessor.java
   branches/branch_5_0/connector-j/src/com/mysql/jdbc/Statement.java
   branches/branch_5_0/connector-j/src/testsuite/simple/EscapeProcessingTest.java
Log:
If the connection "useTimezone" is set to "true", then also respect timezone
      conversions in escape-processed string literals (e.g. "{ts ...}" and 
      "{t ...}").

Modified: branches/branch_5_0/connector-j/src/com/mysql/jdbc/Connection.java
===================================================================
--- branches/branch_5_0/connector-j/src/com/mysql/jdbc/Connection.java	2005-09-07 16:52:54
UTC (rev 4215)
+++ branches/branch_5_0/connector-j/src/com/mysql/jdbc/Connection.java	2005-09-07 17:12:34
UTC (rev 4216)
@@ -1381,6 +1381,8 @@
 
 	private LRUCache serverSideStatementCache;
 
+	private Calendar sessionCalendar;
+
 	/**
 	 * Creates a connection to a MySQL Server.
 	 * 
@@ -4080,7 +4082,8 @@
 
 		Object escapedSqlResult = EscapeProcessor.escapeSQL(sql,
 				serverSupportsConvertFn(),
-				this);
+				this,
+				getCalendarInstanceForSessionOrNew());
 
 		if (escapedSqlResult instanceof String) {
 			return (String) escapedSqlResult;
@@ -4092,7 +4095,8 @@
 	private CallableStatement parseCallableStatement(String sql)
 			throws SQLException {
 		Object escapedSqlResult = EscapeProcessor.escapeSQL(sql,
-				serverSupportsConvertFn(), this);
+				serverSupportsConvertFn(), this,
+				getCalendarInstanceForSessionOrNew());
 
 		boolean isFunctionCall = false;
 		String parsedSql = null;
@@ -5376,4 +5380,20 @@
 	protected boolean isCursorFetchEnabled() throws SQLException {
 		return (versionMeetsMinimum(5, 0, 2) && getUseCursorFetch());
 	}
+	
+	/**
+	 * Optimization to only use one calendar per-session, or calculate it for
+	 * each call, depending on user configuration
+	 */
+	protected synchronized Calendar getCalendarInstanceForSessionOrNew() {
+		if (getDynamicCalendars()) {
+			return Calendar.getInstance();
+		}
+
+		if (this.sessionCalendar == null) {
+			this.sessionCalendar = Calendar.getInstance();
+		}
+
+		return this.sessionCalendar;
+	}
 }

Modified: branches/branch_5_0/connector-j/src/com/mysql/jdbc/EscapeProcessor.java
===================================================================
--- branches/branch_5_0/connector-j/src/com/mysql/jdbc/EscapeProcessor.java	2005-09-07
16:52:54 UTC (rev 4215)
+++ branches/branch_5_0/connector-j/src/com/mysql/jdbc/EscapeProcessor.java	2005-09-07
17:12:34 UTC (rev 4216)
@@ -30,6 +30,7 @@
 package com.mysql.jdbc;
 
 import java.sql.SQLException;
+import java.sql.Time;
 import java.sql.Timestamp;
 
 import java.util.Calendar;
@@ -97,7 +98,9 @@
 	 *             DOCUMENT ME!
 	 */
 	public static final Object escapeSQL(String sql,
-			boolean serverSupportsConvertFn, Connection conn) throws java.sql.SQLException {
+			boolean serverSupportsConvertFn, 
+			Connection conn,
+			Calendar sessionCalendar) throws java.sql.SQLException {
 		boolean replaceEscapeSequence = false;
 		String escapeSequence = null;
 
@@ -144,7 +147,8 @@
 
 							Object remainingResults = escapeSQL(token
 									.substring(1, token.length() - 1),
-									serverSupportsConvertFn, conn);
+									serverSupportsConvertFn, conn,
+									sessionCalendar);
 
 							String remaining = null;
 
@@ -293,8 +297,11 @@
 									.append(minute).append(":").append(second)
 									.append("'");
 							} else {
-								Calendar localTzCal = Calendar.getInstance();
 								
+								if (sessionCalendar == null) {
+									sessionCalendar = Calendar.getInstance();
+								}
+								
 								try {
 									int year4Int = Integer.parseInt(year4);
 									int month2Int = Integer.parseInt(month2);
@@ -305,7 +312,7 @@
 									
 									
 									Timestamp toBeAdjusted = TimeUtil.fastTimestampCreate(
-											localTzCal,
+											sessionCalendar,
 											year4Int,
 											month2Int,
 											day2Int,
@@ -317,7 +324,7 @@
 									Timestamp inServerTimezone = TimeUtil.changeTimezone(
 											conn,
 											toBeAdjusted,
-											localTzCal.getTimeZone(),
+											sessionCalendar.getTimeZone(),
 											conn.getServerTimezoneTZ(),
 											false);
 									
@@ -364,9 +371,45 @@
 							String hour = st.nextToken();
 							String minute = st.nextToken();
 							String second = st.nextToken();
-							String timeString = "'" + hour + ":" + minute + ":"
+							
+							if (!conn.getUseTimezone()) {
+								String timeString = "'" + hour + ":" + minute + ":"
 									+ second + "'";
-							newSql.append(timeString);
+								newSql.append(timeString);
+							} else {
+								if (sessionCalendar == null) {
+									sessionCalendar = Calendar.getInstance();
+								}
+								
+								try {
+									int hourInt = Integer.parseInt(hour);
+									int minuteInt = Integer.parseInt(minute);
+									int secondInt = Integer.parseInt(second);
+									
+									
+									Time toBeAdjusted = TimeUtil.fastTimeCreate(
+											sessionCalendar,
+											hourInt,
+											minuteInt,
+											secondInt);
+									
+									Time inServerTimezone = TimeUtil.changeTimezone(
+											conn,
+											toBeAdjusted,
+											sessionCalendar.getTimeZone(),
+											conn.getServerTimezoneTZ(),
+											false);
+									
+									newSql.append("'");
+									newSql.append(inServerTimezone.toString());
+									newSql.append("'");			
+								
+								} catch (NumberFormatException nfe) {
+									throw new SQLException("Syntax error in TIMESTAMP escape sequence '" 
+										+ token + "'.",
+										SQLError.SQL_STATE_ILLEGAL_ARGUMENT);
+								}
+							}
 						} catch (java.util.NoSuchElementException e) {
 							throw new SQLException(
 									"Syntax error for escape sequence '"

Modified: branches/branch_5_0/connector-j/src/com/mysql/jdbc/Statement.java
===================================================================
--- branches/branch_5_0/connector-j/src/com/mysql/jdbc/Statement.java	2005-09-07 16:52:54
UTC (rev 4215)
+++ branches/branch_5_0/connector-j/src/com/mysql/jdbc/Statement.java	2005-09-07 17:12:34
UTC (rev 4216)
@@ -34,6 +34,7 @@
 import java.sql.Types;
 
 import java.util.ArrayList;
+import java.util.Calendar;
 import java.util.Iterator;
 import java.util.List;
 import java.util.Locale;
@@ -165,6 +166,8 @@
 	/** The warnings chain. */
 	protected SQLWarning warningChain = null;
 
+	private Calendar sessionCalendar;
+
 	/**
 	 * Constructor for a Statement.
 	 * 
@@ -451,7 +454,8 @@
 		if (this.doEscapeProcessing) {
 			Object escapedSqlResult = EscapeProcessor.escapeSQL(sql,
 					this.connection.serverSupportsConvertFn(),
-					this.connection);
+					this.connection,
+					getCalendarInstanceForSessionOrNew());
 
 			if (escapedSqlResult instanceof String) {
 				sql = (String) escapedSqlResult;
@@ -749,7 +753,8 @@
 		if (this.doEscapeProcessing) {
 			Object escapedSqlResult = EscapeProcessor.escapeSQL(sql,
 					this.connection.serverSupportsConvertFn(),
-					this.connection);
+					this.connection,
+					getCalendarInstanceForSessionOrNew());
 
 			if (escapedSqlResult instanceof String) {
 				sql = (String) escapedSqlResult;
@@ -907,7 +912,8 @@
 		if (this.doEscapeProcessing) {
 			Object escapedSqlResult = EscapeProcessor.escapeSQL(sql,
 					this.connection.serverSupportsConvertFn(),
-					this.connection);
+					this.connection,
+					getCalendarInstanceForSessionOrNew());
 
 			if (escapedSqlResult instanceof String) {
 				sql = (String) escapedSqlResult;
@@ -1880,4 +1886,20 @@
 	protected synchronized ResultSet getResultSetInternal() {
 		return this.results;
 	}
+	
+	/**
+	 * Optimization to only use one calendar per-session, or calculate it for
+	 * each call, depending on user configuration
+	 */
+	protected synchronized Calendar getCalendarInstanceForSessionOrNew() {
+		if (this.connection.getDynamicCalendars()) {
+			return Calendar.getInstance();
+		}
+
+		if (this.sessionCalendar == null) {
+			this.sessionCalendar = Calendar.getInstance();
+		}
+
+		return this.sessionCalendar;
+	}
 }

Modified: branches/branch_5_0/connector-j/src/testsuite/simple/EscapeProcessingTest.java
===================================================================
---
branches/branch_5_0/connector-j/src/testsuite/simple/EscapeProcessingTest.java	2005-09-07
16:52:54 UTC (rev 4215)
+++
branches/branch_5_0/connector-j/src/testsuite/simple/EscapeProcessingTest.java	2005-09-07
17:12:34 UTC (rev 4216)
@@ -24,6 +24,10 @@
  */
 package testsuite.simple;
 
+import java.sql.Connection;
+import java.util.Properties;
+import java.util.TimeZone;
+
 import testsuite.BaseTestCase;
 
 /**
@@ -94,4 +98,39 @@
 		assertEquals(conn.nativeSQL("{fn convert(abcd, SQL_INTEGER)}"), conn
 				.nativeSQL("{fn convert(abcd, INTEGER)}"));
 	}
+	
+	/**
+	 * Tests that the escape tokenizer converts timestamp values
+	 * wrt. timezones when useTimezone=true.
+	 * 
+	 * @throws Exception if the test fails.
+	 */
+	public void testTimestampConversion() throws Exception {
+		TimeZone currentTimezone = TimeZone.getDefault();
+		String[] availableIds = TimeZone.getAvailableIDs(currentTimezone.getRawOffset() + (3600
* 1000 * 2));
+		String newTimezone = null;
+		
+		if (availableIds.length > 0) {
+			newTimezone = availableIds[0];
+		} else {
+			newTimezone = "UTC"; // punt
+		}
+		
+		Properties props = new Properties();
+		
+		props.setProperty("useTimezone", "true");
+		props.setProperty("serverTimezone", newTimezone);
+		Connection tzConn = null;
+		
+		try {
+			String escapeToken = "SELECT {ts '2002-11-12 10:00:00'} {t '05:11:02'}";
+			tzConn = getConnectionWithProps(props);
+			assertTrue(!tzConn.nativeSQL(escapeToken).equals(this.conn.nativeSQL(escapeToken)));
+		} finally {
+			if (tzConn != null) {
+				tzConn.close();
+			}
+		}
+		
+	}
 }

Thread
Connector/J commit: r4216 - in branches/branch_5_0/connector-j/src: com/mysql/jdbc testsuite/simplemmatthews7 Sep