1 22 23 package org.xquark.extractor.metadata; 24 25 import java.io.*; 26 import java.io.InputStream ; 27 import java.io.Reader ; 28 import java.math.BigDecimal ; 29 import java.sql.ResultSet ; 30 import java.sql.SQLException ; 31 import java.sql.Timestamp ; 32 import java.text.ParseException ; 33 34 import org.xquark.extractor.common.MetaDataException; 35 import org.xquark.jdbc.typing.*; 36 import org.xquark.schema.SchemaException; 37 import org.xquark.schema.SimpleType; 38 import org.xquark.schema.datatypes.*; 39 import org.xquark.schema.datatypes.URI.MalformedURIException; 40 import org.xquark.schema.validation.ValidationContextProvider; 41 import org.xquark.xquery.parser.XQueryException; 42 import org.xquark.xquery.typing.QAtomicSerializer; 43 44 52 public class ExtractorMappingInfo extends MappingInfo 53 { 54 private static int BUF_SIZE = 256; 55 56 private boolean isBuiltInXMLType = true; 57 private ColumnMetaData columnMetaData = null; 58 59 60 private boolean useGetString = false; 61 62 63 68 public ExtractorMappingInfo(DbType cmeta, TypeMap typeMap) 69 throws MetaDataException 70 { 71 setXMLType(generateSimpleType(cmeta)); 72 setDBType(cmeta); 73 useGetString = typeMap.useGetString(dbType.getJDBCType()); 74 } 75 76 82 public ExtractorMappingInfo(ColumnMetaData cmeta, TypeMap typeMap) 83 throws MetaDataException 84 { 85 this(cmeta.getType(), typeMap); 86 setColumnMetaData(cmeta); 87 } 88 89 97 public ExtractorMappingInfo(SimpleType XMLType, TypeMap typeMap) 98 { 99 super(XMLType); 100 useGetString = typeMap.useGetString( 101 ABSTRACT_SCHEMA_JDBC_MAPPING[sType.getPrimitive().getType()]); 102 } 103 104 107 public void checkForExtraction() throws XQueryException { 108 if (columnMetaData != null && !columnMetaData.getSqlType().isExtraction()) 109 throw new XQueryException("Extraction is not supported for the " + columnMetaData.getTypeName() + " data type."); 110 } 111 112 private String generateSimpleType(DbType dbType) 113 throws MetaDataException 114 { 115 StringBuffer buffer = new StringBuffer (); 116 isBuiltInXMLType = true; 117 switch (dbType.getJDBCType()) { 118 case java.sql.Types.ARRAY : 119 throw new MetaDataException("The JDBC ARRAY type is not currently supported for extraction."); 120 case java.sql.Types.BIGINT : 121 buffer.append("long"); 122 break; 123 case java.sql.Types.BINARY : 124 isBuiltInXMLType = false; 125 buffer.append("<simpleType><restriction base=\"base64Binary\"><length value=\""); 126 buffer.append(dbType.getLength()); 127 buffer.append("\"/></restriction></simpleType>"); 128 break; 129 case java.sql.Types.BIT : case DbType.BOOLEAN : 130 buffer.append("boolean"); 131 break; 132 case java.sql.Types.CHAR : 133 isBuiltInXMLType = false; 134 buffer.append("<simpleType><restriction base=\"string\"><length value=\""); 135 buffer.append(dbType.getLength()); 136 buffer.append("\"/></restriction></simpleType>"); 137 break; 138 case java.sql.Types.DATE : 139 buffer.append("date"); 140 break; 141 case java.sql.Types.DECIMAL : case java.sql.Types.NUMERIC : 142 isBuiltInXMLType = false; 143 buffer.append("<simpleType><restriction base=\"decimal\"><totalDigits value=\""); 144 buffer.append(dbType.getLength()); 145 buffer.append("\"/><fractionDigits value=\""); 146 buffer.append(dbType.getScale()); 147 buffer.append("\"/></restriction></simpleType>"); 148 break; 149 case java.sql.Types.DISTINCT : 150 throw new MetaDataException("The JDBC CLOB type is not currently supported for extraction."); 151 case java.sql.Types.DOUBLE : case java.sql.Types.FLOAT : 152 buffer.append("double"); 153 break; 154 case DbType.ORACLE_ROWID: 155 buffer.append("string"); 156 break; 157 case java.sql.Types.INTEGER : 158 buffer.append("integer"); 159 break; 160 case java.sql.Types.JAVA_OBJECT : 161 throw new MetaDataException("The JDBC JAVA_OBJECT type is not currently supported for extraction."); 162 case java.sql.Types.NULL : 163 throw new MetaDataException("The JDBC NULL type is not currently supported for extraction."); 164 case java.sql.Types.OTHER : 165 throw new MetaDataException("The JDBC OTHER type is not currently supported for extraction."); 166 case java.sql.Types.REAL : 167 buffer.append("float"); 168 break; 169 case java.sql.Types.REF : 170 throw new MetaDataException("The JDBC REF type is not currently supported for extraction."); 171 case java.sql.Types.SMALLINT : 172 buffer.append("short"); 173 break; 174 case java.sql.Types.STRUCT : 175 throw new MetaDataException("The JDBC STRUCT type is not currently supported for extraction."); 176 case java.sql.Types.TIME : 177 buffer.append("time"); 178 break; 179 case java.sql.Types.TIMESTAMP : 180 buffer.append("dateTime"); 181 break; 182 case java.sql.Types.TINYINT : 183 buffer.append("byte"); 184 break; 185 case java.sql.Types.BLOB : 186 case java.sql.Types.LONGVARBINARY : case java.sql.Types.VARBINARY : 187 isBuiltInXMLType = false; 188 buffer.append("<simpleType><restriction base=\"base64Binary\"><maxLength value=\""); 189 buffer.append(dbType.getLength()); 190 buffer.append("\"/></restriction></simpleType>"); 191 break; 192 case java.sql.Types.CLOB : 193 case java.sql.Types.LONGVARCHAR : case java.sql.Types.VARCHAR : 194 isBuiltInXMLType = false; 195 buffer.append("<simpleType><restriction base=\"string\"><maxLength value=\""); 196 buffer.append(dbType.getLength()); 197 buffer.append("\"/></restriction></simpleType>"); 198 break; 199 } 200 return buffer.toString(); 201 } 202 203 public boolean isBuiltInXMLType() { 204 return isBuiltInXMLType; 205 } 206 207 public String getParameter(ResultSet rs, int i, QAtomicSerializer qSerializer, ValidationContextProvider nsContext) throws XQueryException { 208 String value = null; 209 try { 210 if (useGetString) { 211 try { 212 value = rs.getString(i); 214 if (value == null) 215 return null; 216 switch(javaType) { 217 case JAVA_FLOAT : case JAVA_DOUBLE : 219 case JAVA_LONG : case JAVA_BIG_DECIMAL : 220 return qSerializer.removeNotSignificantDigits(value); 221 222 case JAVA_STRING : 223 return qSerializer.serialize(sType, value); 224 case SCHEMA_QNAME : 225 return qSerializer.serialize(new QName(value)); 226 case SCHEMA_URI : 227 return qSerializer.serialize(new URI(value)); 228 case SCHEMA_DATETIME : 229 return qSerializer.serialize(sType, (DateTime)sType.convert(value, true, nsContext)); 230 case SCHEMA_DURATION : 231 return qSerializer.serialize(sType, new Duration(value)); 232 case JAVA_BOOLEAN : 233 return qSerializer.serialize(sType, (Boolean )sType.convert(value, true, nsContext)); 234 case SCHEMA_BYTE_ARRAY : 235 return qSerializer.serialize(sType, (ByteArray)sType.convert(value, true, nsContext)); 236 default: 237 return null; 238 } 239 } 240 catch (SchemaException e1) { 241 throw new XQueryException("Schema exception raised when converting \"" 242 + value + "\" database value to XML. Please check underlying exception.", e1); 243 } 244 catch (SQLException e1) { 245 throw new XQueryException("JDBC exception raised when retrieving data from resultset using backup getString() method. Please check underlying exception.", e1); 246 } 247 } 248 else { 249 switch(javaType) { 250 case JAVA_STRING : 251 if (useStreams){ 252 Reader reader = rs.getCharacterStream(i); 253 char[] cb = new char[BUF_SIZE]; 254 CharArrayWriter caw = new CharArrayWriter(); 255 int len = -1; 256 try { 257 while ((len = reader.read(cb)) > 0) 258 caw.write(cb, 0, len); 259 } catch (IOException e1) { 260 throw new XQueryException( 261 "IOexception raised when retrieving data from resultset using backup getCharacterStream() method. Please check underlying exception.", 262 e1); 263 } 264 if (caw.size() == 0 && rs.wasNull()) 265 value = null; 266 else 267 value = caw.toString(); 268 } 269 else 270 value = rs.getString(i); 271 if (value == null) 272 return null; 273 return qSerializer.serialize(sType, value); 274 case SCHEMA_QNAME : 275 value = rs.getString(i); 276 if (value == null) 277 return null; 278 return qSerializer.serialize(new QName(value)); 279 case SCHEMA_URI : 280 value = rs.getString(i); 281 if (value == null) 282 return null; 283 return qSerializer.serialize(new URI(value)); 284 case SCHEMA_DATETIME : 285 Timestamp ts = rs.getTimestamp(i); 286 if (ts == null) 287 return null; 288 return qSerializer.serialize(sType, new DateTime(ts.getTime())); 289 case SCHEMA_DURATION : 290 value = rs.getString(i); 291 if (value == null) 292 return null; 293 return qSerializer.serialize(sType, new Duration(value)); 294 case JAVA_LONG : 295 long l = rs.getLong(i); 296 if (rs.wasNull()) 297 return null; 298 return qSerializer.serialize(new Long (l)); 299 case JAVA_BIG_DECIMAL : 300 BigDecimal bd = rs.getBigDecimal(i); 301 if (bd == null) 302 return null; 303 return qSerializer.serialize(bd); 304 case JAVA_FLOAT : 305 float f = rs.getFloat(i); 306 if (rs.wasNull()) 307 return null; 308 return qSerializer.serialize(new Float (f)); 309 case JAVA_DOUBLE : 310 double d = rs.getDouble(i); 311 if (rs.wasNull()) 312 return null; 313 return qSerializer.serialize(new Double (d)); 314 case JAVA_BOOLEAN : 315 boolean b = rs.getBoolean(i); 316 if (rs.wasNull()) 317 return null; 318 return qSerializer.serialize(sType, new Boolean (b)); 319 case SCHEMA_BYTE_ARRAY : 320 byte[] ba = null; 321 if (useStreams){ 322 InputStream is = rs.getBinaryStream(i); 323 ba = new byte[BUF_SIZE]; 324 ByteArrayOutputStream baos = new ByteArrayOutputStream(); 325 int len = -1; 326 try { 327 while ((len = is.read(ba)) > 0) 328 baos.write(ba, 0, len); 329 } catch (IOException e1) { 330 throw new XQueryException( 331 "IOexception raised when retrieving data from resultset using backup getCharacterStream() method. Please check underlying exception.", 332 e1); 333 } 334 if (baos.size() == 0 && rs.wasNull()) 335 ba = null; 336 else 337 ba = baos.toByteArray(); 338 } 339 else 340 ba = rs.getBytes(i); 341 if (ba == null) 342 return null; 343 return qSerializer.serialize(sType, ba); 344 default: 345 return null; 346 } 347 } 348 } 349 catch (SQLException e) { 350 try { 351 value = rs.getString(i); 355 return sType.toXMLString(sType.convert(value, true, nsContext), nsContext); 356 } 357 catch (SQLException e1) { 358 throw new XQueryException("JDBC exception raised when retrieving data from resultset using backup getString() method. Please check underlying exception.", e1); 359 } 360 catch (SchemaException e1) { 361 throw new XQueryException("Schema exception raised when converting \"" 362 + value + "\" database value to XML. Please check underlying exception.", e1); 363 } 364 } 365 catch (MalformedURIException e) { 366 throw new XQueryException("Data retrieved from resultset is not an URI. Please check underlying exception.", e); 367 } 368 catch (ParseException e) { 369 throw new XQueryException("Data retrieved from resultset is not a Duration. Please check underlying exception.", e); 370 } 371 } 372 373 public ColumnMetaData getColumnMetaData() { 374 return columnMetaData; 375 } 376 377 public void setColumnMetaData(ColumnMetaData columnMetaData) { 378 this.columnMetaData = columnMetaData; 379 } 380 } 381 | Popular Tags |