1 24 25 package org.objectweb.cjdbc.common.sql; 26 27 import java.io.IOException ; 28 import java.io.Serializable ; 29 import java.sql.SQLException ; 30 import java.util.ArrayList ; 31 import java.util.StringTokenizer ; 32 33 import org.objectweb.cjdbc.common.sql.schema.AliasedDatabaseTable; 34 import org.objectweb.cjdbc.common.sql.schema.DatabaseColumn; 35 import org.objectweb.cjdbc.common.sql.schema.DatabaseSchema; 36 import org.objectweb.cjdbc.common.sql.schema.DatabaseTable; 37 import org.objectweb.cjdbc.common.sql.schema.TableColumn; 38 import org.objectweb.cjdbc.common.stream.CJDBCInputStream; 39 40 56 public class DeleteRequest extends AbstractWriteRequest implements Serializable 57 { 58 private static final long serialVersionUID = 6112365011840943168L; 59 60 61 private transient boolean isUnique = false; 62 63 64 private transient ArrayList from; 65 66 79 protected ArrayList whereValues; 80 81 99 public DeleteRequest(String sqlQuery, boolean escapeProcessing, int timeout, 100 String lineSeparator, DatabaseSchema schema, int granularity, 101 boolean isCaseSensitive) throws SQLException 102 { 103 this(sqlQuery, escapeProcessing, timeout, lineSeparator); 104 parse(schema, granularity, isCaseSensitive); 105 } 106 107 122 public DeleteRequest(String sqlQuery, boolean escapeProcessing, int timeout, 123 String lineSeparator) 124 { 125 super(sqlQuery, escapeProcessing, timeout, lineSeparator, 126 RequestType.DELETE); 127 } 128 129 132 public DeleteRequest(CJDBCInputStream in) throws IOException 133 { 134 super(in, RequestType.DELETE); 135 } 136 137 152 public void parse(DatabaseSchema schema, int granularity, 153 boolean isCaseSensitive) throws SQLException 154 { 155 if (granularity == ParsingGranularities.NO_PARSING) 156 { 157 isParsed = true; 158 return; 159 } 160 161 if (schema == null) 163 throw new SQLException ( 164 "Unable to parse request with an undefined database schema"); 165 166 String originalSQL = this.trimCarriageReturnAndTabs(); 167 String sql = originalSQL.toLowerCase(); 168 169 int fromIdx = sql.indexOf("from "); 170 if (fromIdx == -1) 171 { 172 fromIdx = 6; } 175 else 176 { 177 String tableBetweenDeleteAndFrom; 182 if (isCaseSensitive) 183 tableBetweenDeleteAndFrom = originalSQL.substring(6, fromIdx).trim(); 184 else 185 tableBetweenDeleteAndFrom = sql.substring(6, fromIdx).trim(); 186 if (tableBetweenDeleteAndFrom.length() == 0) 187 tableName = null; 188 else 189 tableName = tableBetweenDeleteAndFrom; 190 fromIdx += 5; } 192 193 sql = sql.substring(fromIdx).trim(); 194 195 int whereIdx = sql.indexOf("where "); 197 198 if (isCaseSensitive) 199 sql = originalSQL.substring(originalSQL.length() - sql.length()); 200 if (tableName == null) 201 { if (whereIdx == -1) 203 tableName = sql; 204 else 205 tableName = sql.substring(0, whereIdx).trim(); 206 } 207 208 DatabaseTable t = schema.getTable(tableName, isCaseSensitive); 210 if (t == null) 211 throw new SQLException ("Unknown table '" + tableName 212 + "' in this DELETE statement: " + sqlQuery + "'"); 213 else 214 tableName = t.getName(); 216 217 try 218 { 219 switch (granularity) 220 { 221 case ParsingGranularities.NO_PARSING : 222 return; 223 case ParsingGranularities.TABLE : 224 break; 225 case ParsingGranularities.COLUMN : 226 from = getFromTables(tableName, schema); 227 columns = getWhereColumns(sql.substring(whereIdx + 6).trim(), from); 228 229 if (from != null) 230 { 231 int size = from.size(); 234 ArrayList unaliased = new ArrayList (size); 235 for (int i = 0; i < size; i++) 236 unaliased.add(((AliasedDatabaseTable) from.get(i)).getTable() 237 .getName()); 238 from = unaliased; 239 } 240 break; 241 case ParsingGranularities.COLUMN_UNIQUE : 242 from = getFromTables(tableName, schema); 243 columns = getWhereColumns(sql.substring(whereIdx + 6).trim(), from); 244 245 if (from != null) 246 { 247 int size = from.size(); 250 ArrayList unaliased = new ArrayList (size); 251 for (int i = 0; i < size; i++) 252 unaliased.add(((AliasedDatabaseTable) from.get(i)).getTable() 253 .getName()); 254 from = unaliased; 255 } 256 break; 257 default : 258 throw new SQLException ("Unsupported parsing granularity: '" 259 + granularity + "'"); 260 } 261 } 262 catch (SQLException e) 263 { 264 from = null; 265 columns = null; 266 whereValues = null; 267 throw e; 268 } 269 270 isParsed = true; 271 } 272 273 276 public void cloneParsing(AbstractRequest request) 277 { 278 if (!request.isParsed()) 279 return; 280 cloneTableNameAndColumns((AbstractWriteRequest) request); 281 isParsed = true; 282 } 283 284 295 private ArrayList getFromTables(String fromClause, DatabaseSchema dbs) 296 throws SQLException 297 { 298 StringTokenizer tables = new StringTokenizer (fromClause, ","); 299 ArrayList result = new ArrayList (tables.countTokens()); 300 while (tables.hasMoreTokens()) 301 { 302 String tableName = tables.nextToken().trim(); 303 String alias = null; 306 int aliasIdx = tableName.indexOf(' '); 307 if (aliasIdx != -1) 308 { 309 alias = tableName.substring(aliasIdx); 310 tableName = tableName.substring(0, aliasIdx); 311 } 312 313 DatabaseTable table = dbs.getTable(tableName); 314 if (table == null) 315 throw new SQLException ("Unknown table '" + tableName 316 + "' in FROM clause of this DELETE statement: '" + sqlQuery + "'"); 317 result.add(new AliasedDatabaseTable(table, alias)); 318 } 319 320 return result; 321 } 322 323 336 private ArrayList getWhereColumns(String whereClause, ArrayList aliasedFrom) 337 { 338 ArrayList result = new ArrayList (); ArrayList dbColumns = new ArrayList (); 341 DatabaseColumn col; 344 for (int i = 0; i < aliasedFrom.size(); i++) 345 { 346 DatabaseTable t = ((AliasedDatabaseTable) aliasedFrom.get(i)).getTable(); 347 ArrayList cols = t.getColumns(); 348 int size = cols.size(); 349 for (int j = 0; j < size; j++) 350 { 351 col = (DatabaseColumn) cols.get(j); 352 int matchIdx = whereClause.indexOf(col.getName()); 355 while (matchIdx > 0) 356 { 357 char beforePattern = whereClause.charAt(matchIdx - 1); 359 if (((beforePattern >= 'a') && (beforePattern <= 'z')) || (beforePattern == '_')) 362 matchIdx = whereClause.indexOf(col.getName(), matchIdx + 1); 363 else 364 break; 365 } 366 if (matchIdx == -1) 367 continue; 368 result.add(new TableColumn(t.getName(), col.getName())); 369 if (col.isUnique()) 370 pkValue = col.getName(); 371 dbColumns.add(col); 372 } 373 } 374 375 return result; 376 } 377 378 385 public ArrayList getValues() 386 { 387 return whereValues; 388 } 389 390 395 public boolean isUnique() 396 { 397 return isUnique; 398 } 399 400 403 public boolean needsMacroProcessing() 404 { 405 return true; 406 } 407 408 411 public boolean returnsResultSet() 412 { 413 return false; 414 } 415 416 419 public void debug() 420 { 421 super.debug(); 422 System.out.println("Is unique: " + isUnique); 423 if (tableName != null) 424 System.out.println("Deleted table: " + tableName); 425 else 426 System.out.println("No information about deleted table"); 427 428 if (columns != null) 429 { 430 System.out.println("Columns columns:"); 431 for (int i = 0; i < columns.size(); i++) 432 System.out.println(" " 433 + ((TableColumn) columns.get(i)).getColumnName()); 434 } 435 else 436 System.out.println("No information about updated columns"); 437 438 System.out.println(); 439 } 440 } | Popular Tags |