Coverage Report - net.wotonomy.access.EOSQLExpression
 
Classes in this File Line Coverage Branch Coverage Complexity
EOSQLExpression
0% 
0% 
2.203
 
 1  
 /*
 2  
 Wotonomy: OpenStep design patterns for pure Java applications.
 3  
 Copyright (C) 2000 Michael Powers
 4  
 
 5  
 This library is free software; you can redistribute it and/or
 6  
 modify it under the terms of the GNU Lesser General Public
 7  
 License as published by the Free Software Foundation; either
 8  
 version 2.1 of the License, or (at your option) any later version.
 9  
 
 10  
 This library is distributed in the hope that it will be useful,
 11  
 but WITHOUT ANY WARRANTY; without even the implied warranty of
 12  
 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 13  
 Lesser General Public License for more details.
 14  
 
 15  
 You should have received a copy of the GNU Lesser General Public
 16  
 License along with this library; if not, see http://www.gnu.org
 17  
 */
 18  
 package net.wotonomy.access;
 19  
 
 20  
 import java.util.Enumeration;
 21  
 
 22  
 import net.wotonomy.control.EOAndQualifier;
 23  
 import net.wotonomy.control.EOFetchSpecification;
 24  
 import net.wotonomy.control.EOKeyComparisonQualifier;
 25  
 import net.wotonomy.control.EOKeyValueQualifier;
 26  
 import net.wotonomy.control.EOOrQualifier;
 27  
 import net.wotonomy.control.EOQualifier;
 28  
 import net.wotonomy.control.EOSortOrdering;
 29  
 import net.wotonomy.foundation.NSArray;
 30  
 import net.wotonomy.foundation.NSData;
 31  
 import net.wotonomy.foundation.NSDictionary;
 32  
 import net.wotonomy.foundation.NSKeyValueCoding;
 33  
 import net.wotonomy.foundation.NSMutableArray;
 34  
 import net.wotonomy.foundation.NSMutableDictionary;
 35  
 import net.wotonomy.foundation.NSSelector;
 36  
 import net.wotonomy.foundation.NSTimestamp;
 37  
 import net.wotonomy.foundation.NSTimestampFormatter;
 38  
 
 39  
 /**
 40  
 * @author ezamudio@nasoft.com
 41  
 * @author $Author: cgruber $
 42  
 * @version $Revision: 894 $
 43  
 */
 44  0
 public abstract class EOSQLExpression {
 45  
 
 46  
         public static final String BindVariableAttributeKey = "BindVariableAttribute";
 47  
         public static final String BindVariableColumnKey = "BindVariableColumn";
 48  
         public static final String BindVariableNameKey = "BindVariableName";
 49  
         public static final String BindVariablePlaceHolderKey = "BindVariablePlaceholder";
 50  
         public static final String BindVariableValueKey = "BindVariableValue";
 51  
         private static int UseBindings;
 52  
         private static final int _DefaultFormatSQLStringLength = 64;
 53  
         private static final int _DefaultListStringLength = 256;
 54  
         private static final int _DefaultOrderByStringLength = 128;
 55  
         private static final int _DefaultPathLength = 128;
 56  
         private static final int _DefaultTableListLength = 128;
 57  0
         protected static final char[] _hexChars = new char[]{
 58  0
                 '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'
 59  
         };
 60  
         private static final int _ValueLengthLimit = 40;
 61  
         protected NSMutableDictionary _aliasesByRelationshipPath;
 62  
         protected NSMutableDictionary _aliasesByEntityName;
 63  
         protected NSMutableArray _bindings;
 64  
         protected NSMutableArray _contextStack;
 65  
         protected static NSTimestampFormatter _defaultDateFormatter;
 66  
         protected EOEntity _entity;
 67  
         protected StringBuffer _joinClauseString;
 68  
         protected StringBuffer _listString;
 69  
         protected StringBuffer _orderByString;
 70  
         protected String _statement;
 71  
         protected String _upperFunctionName;
 72  0
         protected boolean _useAliases = true;
 73  
         protected static boolean _quoteExternalNames;
 74  
         protected StringBuffer _valueListString;
 75  
         protected String _whereClauseString;
 76  
 
 77  
         private EOSQLExpression() {
 78  0
                 super();
 79  0
         }
 80  
                     
 81  
         public EOSQLExpression(EOEntity entity) {
 82  0
                 super();
 83  0
                 _entity = entity;
 84  0
         }
 85  
 
 86  
         public String _aliasForRelatedAttributeRelationshipPath(EOAttribute a, String path) {
 87  0
                 return null;
 88  
         }
 89  
 
 90  
         public String _aliasForRelationshipPath(String path) {
 91  0
                 return (String)_aliasesByRelationshipPath.objectForKey(path);
 92  
         }
 93  
 
 94  
         protected NSTimestampFormatter _defaultDateFormatter() {
 95  0
                 return _defaultDateFormatter;
 96  
         }
 97  
 
 98  
         protected StringBuffer _listString() {
 99  0
                 if (_listString == null)
 100  0
                         _listString = new StringBuffer();
 101  0
                 return _listString;
 102  
         }
 103  
 
 104  
         protected StringBuffer _orderByString() {
 105  0
                 if (_orderByString == null)
 106  0
                         _orderByString = new StringBuffer();
 107  0
                 return _orderByString;
 108  
         }
 109  
 
 110  
         public EOEntity _rootEntityForExpression() {
 111  0
                 return _entity;
 112  
         }
 113  
 
 114  
         public void _setEntity(EOEntity value) {
 115  0
                 _entity = value;
 116  0
         }
 117  
 
 118  
         public String _sqlStringForJoinSemanticMatchSemantic(int semantic,int match) {
 119  0
                 return null;
 120  
         }
 121  
 
 122  
         protected String _stringForDate(NSTimestamp timestamp) {
 123  0
                 return null;
 124  
         }
 125  
 
 126  
         protected StringBuffer _valueList() {
 127  0
                 if (_valueListString == null)
 128  0
                         _valueListString = new StringBuffer();
 129  0
                 return _valueListString;
 130  
         }
 131  
 
 132  
         public void addBindVariableDictionary( NSDictionary dict ) {
 133  0
         }
 134  
 
 135  
         /** Adds the SQL to create the attribute to the attribute list.
 136  
          * The appended text is of the form attr_name attr_type allow_null
 137  
          * @param attr The attribute to create the SQL for.
 138  
          */
 139  
         public void addCreateClauseForAttribute(EOAttribute attr) {
 140  0
                 StringBuffer buf = new StringBuffer(attr.columnName());
 141  0
                 buf.append(' ');
 142  0
                 buf.append(columnTypeStringForAttribute(attr));
 143  0
                 buf.append(allowsNullClauseForConstraint(attr.allowsNull()));
 144  0
                 appendItemToListString(buf.toString(), _listString());
 145  0
         }
 146  
 
 147  
         public void addInsertListAttribute(EOAttribute attr, Object o) {
 148  0
         }
 149  
 
 150  
         public void addJoinClause(String left, String right, int semantic) {
 151  0
                 String s = assembleJoinClause(left, right, semantic);
 152  0
                 if (_joinClauseString == null)
 153  0
                         _joinClauseString = new StringBuffer();
 154  0
                 if (_joinClauseString.length() > 0)
 155  0
                         _joinClauseString.append(" AND ");
 156  0
                 _joinClauseString.append(s);
 157  0
         }
 158  
 
 159  
         public void addOrderByAttributeOrdering(EOSortOrdering order) {
 160  0
                 String sql = sqlStringForAttributeNamed(order.key());
 161  0
                 if (order.selector().equals(EOSortOrdering.CompareCaseInsensitiveAscending) || order.selector().equals(EOSortOrdering.CompareCaseInsensitiveDescending))
 162  0
                         sql = "UPPER(" + sql + ")";
 163  0
                 if (order.selector().equals(EOSortOrdering.CompareCaseInsensitiveAscending) || order.selector().equals(EOSortOrdering.CompareAscending))
 164  0
                         sql += " ASC";
 165  
                 else
 166  0
                         sql += " DESC";
 167  0
                 appendItemToListString(sql, _orderByString());
 168  0
         }
 169  
 
 170  
         public void addSelectListAttribute(EOAttribute attr) {
 171  0
                 appendItemToListString(formatSQLString(sqlStringForAttribute(attr), attr.readFormat()), _listString());
 172  0
         }
 173  
 
 174  
         public void addUpdateListAttribute(EOAttribute attr, Object o) {
 175  0
                 StringBuffer buf = new StringBuffer(attr.columnName());
 176  0
                 buf.append('=');
 177  0
                 buf.append(formatSQLString(formatValueForAttribute(o, attr), attr.writeFormat()));
 178  0
                 appendItemToListString(buf.toString(), _listString());
 179  0
         }
 180  
 
 181  
         public NSMutableDictionary aliasesByRelationshipPath() {
 182  0
                 if (_aliasesByRelationshipPath == null) {
 183  0
                         _aliasesByRelationshipPath = new NSMutableDictionary();
 184  0
                         if (!_useAliases)
 185  0
                                 return _aliasesByRelationshipPath;
 186  0
                         _aliasesByRelationshipPath.setObjectForKey("t0", "");
 187  
                 }
 188  0
                 return _aliasesByRelationshipPath;
 189  
         }
 190  
 
 191  
         public String allowsNullClauseForConstraint(boolean flag) {
 192  0
                 return flag ? "" : " NOT NULL";
 193  
         }
 194  
 
 195  
         public void appendItemToListString(String item, StringBuffer list) {
 196  0
                 if (list.length() > 0)
 197  0
                         list.append(", ");
 198  0
                 list.append(item);
 199  0
         }
 200  
 
 201  
         public String assembleDeleteStatementWithQualifier(EOQualifier q, String tableList, String whereClause) {
 202  0
                 String s = "DELETE FROM " + tableList;
 203  0
                 if (whereClause != null && whereClause.length() > 0)
 204  0
                         s += " WHERE " + whereClause;
 205  0
                 return s;
 206  
         }
 207  
 
 208  
         public String assembleInsertStatementWithRow(NSDictionary row,
 209  
                         String tableList, String columnList, String valueList) {
 210  0
                 String sql = "INSERT INTO " + tableList;
 211  0
                 if (columnList != null)
 212  0
                         sql += " (" + columnList + ")";
 213  0
                 sql += " VALUES " + valueList;
 214  0
                 return sql;
 215  
         }
 216  
 
 217  
         public String assembleJoinClause(String leftName, String rightName, int semantic) {
 218  0
                 String op = "=";
 219  0
                 if (semantic == EORelationship.LeftOuterJoin)
 220  0
                         op = "*=";
 221  0
                 else if (semantic == EORelationship.RightOuterJoin)
 222  0
                         op = "=*";
 223  0
                 return leftName + op + rightName;
 224  
         }
 225  
 
 226  
         public String assembleSelectStatementWithAttributes(NSArray attributes,
 227  
                         boolean lock, EOQualifier q, NSArray fetchOrder, String selectString, String columnList,
 228  
                         String tableList, String whereClause, String joinClause, String orderByClause, String lockClause) {
 229  0
                 String sql = selectString + " " + columnList + " FROM " + tableList;
 230  0
                 if (lockClause != null)
 231  0
                         sql += " " + lockClause;
 232  0
                 if (whereClause != null || joinClause != null)
 233  0
                         sql += " WHERE ";
 234  0
                 if (whereClause != null)
 235  0
                         sql += whereClause;
 236  0
                 if (whereClause != null && joinClause != null)
 237  0
                         sql += " AND ";
 238  0
                 if (joinClause != null)
 239  0
                         sql += joinClause;
 240  0
                 if (orderByClause != null)
 241  0
                         sql += " ORDER BY " + orderByClause;
 242  0
                 return sql;
 243  
         }
 244  
 
 245  
         public String assembleUpdateStatementWithRow(NSDictionary row, EOQualifier q, String tableList, String updateList, String whereClause) {
 246  0
                 String s = "UPDATE " + tableList + " SET " + updateList;
 247  0
                 if (whereClause != null && whereClause.length() > 0)
 248  0
                         s += " WHERE " + whereClause;
 249  0
                 return s;
 250  
         }
 251  
 
 252  
         public NSArray bindVariableDictionaries() {
 253  0
                 return null;
 254  
         }
 255  
 
 256  
         public abstract NSMutableDictionary bindVariableDictionaryForAttribute(EOAttribute attr, Object o);
 257  
 
 258  
         public String columnTypeStringForAttribute(EOAttribute attr) {
 259  0
                 String x = attr.externalType();
 260  0
                 if (attr.precision() > 0) {
 261  0
                         x += " (" + attr.precision() + "," + attr.scale() + ")";
 262  0
                 } else if (attr.width() > 0) {
 263  0
                         x += " (" + attr.width() + ")";
 264  
                 }
 265  0
                 return x;
 266  
         }
 267  
 
 268  
         public EOEntity entity() {
 269  0
                 return _entity;
 270  
         }
 271  
 
 272  
         public String externalNameQuoteCharacter() {
 273  0
                 return "\"";
 274  
         }
 275  
 
 276  
         public String formatSQLString(String value, String format) {
 277  0
                 if (format == null)
 278  0
                         return value;
 279  0
                 return value;
 280  
         }
 281  
 
 282  
         /**
 283  
          * Returns the received string wrapped in single quotes,
 284  
          * with any quotes or escape chars found inside it
 285  
          * properly escaped.
 286  
          * @param s The string to format.
 287  
          */
 288  
         public String formatStringValue(String s) {
 289  0
                 StringBuffer buf = new StringBuffer(s);
 290  0
                 for (int i = buf.length()-1; i >= 0; i--) {
 291  0
                         if (buf.charAt(i) == sqlEscapeChar()) {
 292  0
                                 buf.insert(i, sqlEscapeChar());
 293  0
                                 i++;
 294  
                         }
 295  0
                         if (buf.charAt(i) == '\'') {
 296  0
                                 buf.insert(i, sqlEscapeChar());
 297  0
                                 i++;
 298  
                         }
 299  
                 }
 300  0
                 buf.append('\'');
 301  0
                 buf.insert(0, '\'');
 302  0
                 return buf.toString();
 303  
         }
 304  
 
 305  
         public String formatValueForAttribute(Object value, EOAttribute attr) {
 306  0
                 if (value == null || value == NSKeyValueCoding.NullValue)
 307  0
                         return "NULL";
 308  0
                 if (value instanceof String)
 309  0
                         return formatStringValue((String)value);
 310  0
                 if (value instanceof Number)
 311  0
                         return sqlStringForNumber((Number)value);
 312  
                 //TODO: format timestamps
 313  0
                 return value.toString();
 314  
         }
 315  
 
 316  
         public String joinClauseString() {
 317  0
                 if (_joinClauseString == null)
 318  0
                         return null;
 319  0
                 return _joinClauseString.toString();
 320  
         }
 321  
 
 322  
         public void joinExpression() {
 323  0
                 _joinClauseString = null;
 324  0
                 if (_aliasesByEntityName.count() > 1) {
 325  
                 }
 326  0
         }
 327  
 
 328  
         public String listString() {
 329  0
                 return _listString().toString();
 330  
         }
 331  
 
 332  
         public String lockClause() {
 333  0
                 return "";
 334  
         }
 335  
 
 336  
         public boolean mustUseBindVariableForAttribute(EOAttribute attr) {
 337  0
                 return false;
 338  
         }
 339  
 
 340  
         public String orderByString() {
 341  0
                 if  (_orderByString == null)
 342  0
                         return null;
 343  0
                 return _orderByString.toString();
 344  
         }
 345  
 
 346  
         public void prepareConstraintStatementForRelationship(EORelationship rel, NSArray arr1, NSArray arr2) {
 347  0
         }
 348  
 
 349  
         public void prepareDeleteExpressionForQualifier(EOQualifier q) {
 350  0
                 String where = null;
 351  0
                 setStatement(assembleDeleteStatementWithQualifier(q, _entity.externalName(), where));
 352  0
         }
 353  
 
 354  
         public void prepareInsertExpressionWithRow(NSDictionary row) {
 355  0
                 StringBuffer cols = new StringBuffer("(");
 356  0
                 StringBuffer values = new StringBuffer("(");
 357  0
                 Enumeration enumeration = row.keyEnumerator();
 358  0
                 while (enumeration.hasMoreElements()) {
 359  0
                         String key = (String)enumeration.nextElement();
 360  0
                         EOAttribute a = _entity.attributeNamed(key);
 361  0
                         cols.append(a.columnName());
 362  0
                         values.append(formatValueForAttribute(row.objectForKey(key), a));
 363  0
                         if (enumeration.hasMoreElements()) {
 364  0
                                 cols.append(", ");
 365  0
                                 values.append(", ");
 366  
                         }
 367  0
                 }
 368  0
                 cols.append(")");
 369  0
                 cols.append(")");
 370  0
                 setStatement(assembleInsertStatementWithRow(row, _entity.externalName(), cols.toString(), values.toString()));
 371  0
         }
 372  
 
 373  
         public void prepareSelectExpressionWithAttributes(NSArray atts, boolean lock, EOFetchSpecification fspec) {
 374  0
                 _aliasesByRelationshipPath = new NSMutableDictionary();
 375  0
                 _aliasesByEntityName = new NSMutableDictionary();
 376  0
                 EOQualifier q = null;
 377  0
                 NSArray order = null;
 378  0
                 if (fspec != null) {
 379  0
                         q = fspec.qualifier();
 380  0
                         order = fspec.sortOrderings();
 381  
                 }
 382  
                 //Assemble the column list (this yields the alias list)
 383  0
                 for (int i = 0; i < atts.count(); i++)
 384  0
                         addSelectListAttribute((EOAttribute)atts.objectAtIndex(i));
 385  
                 //assemble the where string
 386  0
                 if (q != null) {
 387  0
                         if (q instanceof EOQualifierSQLGeneration)
 388  0
                                 setWhereClauseString(sqlStringForQualifier((EOQualifierSQLGeneration)q));
 389  
                         else {
 390  0
                                 EOQualifierSQLGeneration.Support sup = EOQualifierSQLGeneration.Support.supportForClass(q.getClass());
 391  0
                                 setWhereClauseString(sup.sqlStringForSQLExpression(q, this));
 392  
                         }
 393  
                 }
 394  
                 //assemble the join string
 395  0
                 joinExpression();
 396  
                 //assemble the order by string
 397  0
                 if (order != null && order.count() > 0) {
 398  0
                         for (int i = 0; i < order.count(); i++) {
 399  0
                                 EOSortOrdering so = (EOSortOrdering)order.objectAtIndex(i);
 400  0
                                 addOrderByAttributeOrdering(so);
 401  
                         }
 402  
                 }
 403  
                 //create the statement
 404  0
                 setStatement(assembleSelectStatementWithAttributes(atts, lock, q, order, "SELECT", listString(),
 405  0
                         tableListWithRootEntity(_entity), whereClauseString(), joinClauseString(), orderByString(), lockClause()));
 406  0
         }
 407  
 
 408  
         /** Build an UPDATE statement with the given information. */
 409  
         public void prepareUpdateExpressionWithRow(NSDictionary row, EOQualifier q) {
 410  0
                 StringBuffer buf = new StringBuffer();
 411  0
                 Enumeration enumeration = row.keyEnumerator();
 412  0
                 while (enumeration.hasMoreElements()) {
 413  0
                         String key = (String)enumeration.nextElement();
 414  0
                         EOAttribute a = _entity.attributeNamed(key);
 415  0
                         if (a == null)
 416  0
                                 throw new EOGeneralAdaptorException("Cannot find attribute named " + key + " in entity " + _entity.name());
 417  0
                         buf.append(a.columnName());
 418  0
                         buf.append('=');
 419  0
                         buf.append(formatValueForAttribute(row.objectForKey(key), a));
 420  0
                         if (enumeration.hasMoreElements())
 421  0
                                 buf.append(", ");
 422  0
                 }
 423  0
                 if (q != null) {
 424  0
                         setWhereClauseString(sqlStringForQualifier(null));
 425  
                 }
 426  0
                 setStatement(assembleUpdateStatementWithRow(row, q, _entity.externalName(), buf.toString(), whereClauseString()));
 427  0
         }
 428  
 
 429  
         public void setStatement(String statement) {
 430  0
                 _statement = statement;
 431  0
         }
 432  
 
 433  
         public String statement() {
 434  0
                 return _statement;
 435  
         }
 436  
 
 437  
         public void setUseAliases(boolean flag) {
 438  0
                 _useAliases = flag;
 439  0
         }
 440  
 
 441  
         public boolean useAliases() {
 442  0
                 return _useAliases;
 443  
         }
 444  
 
 445  
         public void setUseBindVariables(boolean flag) {
 446  0
         }
 447  
 
 448  
         public boolean useBindVariables() {
 449  0
                 return System.getProperty("EOAdaptorUseBindVariables", "false").equals("true");
 450  
         }
 451  
 
 452  
         /** @deprecated Check externalNameQuoteCharacter instead. */
 453  
         public static void setUseQuotedExternalNames(boolean flag) {
 454  0
                 _quoteExternalNames = flag;
 455  0
         }
 456  
         /** @deprecated Use the instance method externalNameQuoteCharacter instead. */
 457  
         public static boolean useQuotedExternalNames() {
 458  0
                 return _quoteExternalNames;
 459  
         }
 460  
 
 461  
         public void setWhereClauseString(String clause) {
 462  0
                 _whereClauseString = clause;
 463  0
         }
 464  
 
 465  
         public String whereClauseString() {
 466  0
                 return _whereClauseString;
 467  
         }
 468  
 
 469  
         public boolean shouldUseBindVariableForAttribute(EOAttribute attr) {
 470  0
                 return false;
 471  
         }
 472  
 
 473  
         public char sqlEscapeChar() {
 474  0
                 return '\\';
 475  
         }
 476  
 
 477  
         public String sqlPatternFromShellPattern(String pattern) {
 478  0
                 return sqlPatternFromShellPatternWithEscapeCharacter(pattern, sqlEscapeChar());
 479  
         }
 480  
 
 481  
         public String sqlPatternFromShellPatternWithEscapeCharacter(String pattern, char escape) {
 482  0
                 StringBuffer buf = new StringBuffer(pattern);
 483  0
                 int idx = 0;
 484  
                 //escape all '%'
 485  
                 do {
 486  0
                         idx = buf.indexOf("%");
 487  0
                         if (idx == 0)
 488  0
                                 buf.insert(escape, 0);
 489  0
                         else if (idx > 0 && buf.charAt(idx-1) != escape)
 490  0
                                 buf.insert(escape, idx);
 491  0
                 } while (idx >= 0);
 492  
                 //escape all '_'
 493  
                 do {
 494  0
                         idx = buf.indexOf("_");
 495  0
                         if (idx == 0)
 496  0
                                 buf.insert(escape, 0);
 497  0
                         else if (idx > 0 && buf.charAt(idx-1) != escape)
 498  0
                                 buf.insert(escape, idx);
 499  0
                 } while (idx >= 0);
 500  
                 //substitute all '*'
 501  
                 do {
 502  0
                         idx = buf.indexOf("*");
 503  0
                         if (idx >= 0)
 504  0
                                 buf.replace(idx, idx+1, "%");
 505  0
                 } while (idx >= 0);
 506  
                 //substitute all '?'
 507  
                 do {
 508  0
                         idx = buf.indexOf("?");
 509  0
                         if (idx >= 0)
 510  0
                                 buf.replace(idx, idx+1, "_");
 511  0
                 } while (idx >= 0);
 512  0
                 return buf.toString();
 513  
         }
 514  
 
 515  
         public String sqlStringForAttribute(EOAttribute attr) {
 516  0
                 if (_aliasesByEntityName == null)
 517  0
                         _aliasesByEntityName = new NSMutableDictionary();
 518  0
                 String alias = (String)_aliasesByEntityName.objectForKey(attr.entity().name());
 519  0
                 if (alias == null) {
 520  0
                         alias = "t" + (_aliasesByEntityName.count() + 1);
 521  0
                         _aliasesByEntityName.setObjectForKey(alias, attr.entity().name());
 522  
                 }
 523  0
                 if (useAliases())
 524  0
                         return alias + "." + attr.columnName();
 525  
                 else
 526  0
                         return attr.entity().externalName() + "." + attr.columnName();
 527  
         }
 528  
 
 529  
         public String sqlStringForAttributeNamed(String name) {
 530  0
                 if (name.indexOf('.') > 0) {
 531  0
                         return sqlStringForAttribute(_entity._attributeForPath(name));
 532  
                 }
 533  0
                 return sqlStringForAttribute(_entity.attributeNamed(name));
 534  
                 
 535  
         }
 536  
 
 537  
         /**
 538  
          * Returns a string representing the path from the first
 539  
          * relationship in the array to the last one.
 540  
          * @param path An array of EORelationship objects.
 541  
          * @return A string consisting of the names of the relationships
 542  
          * separated by dots.
 543  
          */
 544  
         public String sqlStringForAttributePath(NSArray path) {
 545  0
                 StringBuffer buf = new StringBuffer();
 546  0
                 for (int i = 0; i < path.count(); i++) {
 547  0
                         EORelationship rel = (EORelationship)path.objectAtIndex(i);
 548  0
                         if (i > 0)
 549  0
                                 buf.append('.');
 550  0
                         buf.append(rel.name());
 551  
                 }
 552  0
                 return buf.toString();
 553  
         }
 554  
 
 555  
         public String sqlStringForCaseInsensitiveLike(String key, String value) {
 556  0
                 return "LOWER(" + key + ") LIKE LOWER(" + sqlPatternFromShellPattern(value) + ")";
 557  
         }
 558  
 
 559  
         public String sqlStringForConjoinedQualifiers(NSArray qualifiers) {
 560  0
                 EOAndQualifier q = new EOAndQualifier(qualifiers);
 561  0
                 return EOQualifierSQLGeneration.Support.supportForClass(EOAndQualifier.class).sqlStringForSQLExpression(q, this);
 562  
         }
 563  
 
 564  
         public String sqlStringForData(NSData data) {
 565  0
                 byte[] b = data.bytes();
 566  0
                 char[] c = new char[b.length * 2];
 567  0
                 int pos = 0;
 568  0
                 for (int i = 0; i < b.length; i++) {
 569  0
                         int x = (b[i] & 0xf0) >> 4;
 570  0
                         c[pos++] = _hexChars[x];
 571  0
                         x = (b[i] & 0x0f);
 572  0
                         c[pos++] = _hexChars[x];
 573  
                 }
 574  0
                 return new String(c);
 575  
         }
 576  
 
 577  
         public String sqlStringForDisjoinedQualifiers(NSArray qualifiers) {
 578  0
                 EOOrQualifier q = new EOOrQualifier(qualifiers);
 579  0
                 return EOQualifierSQLGeneration.Support.supportForClass(EOOrQualifier.class).sqlStringForSQLExpression(q, this);
 580  
         }
 581  
 
 582  
         public String sqlStringForKeyComparisonQualifier(EOKeyComparisonQualifier q) {
 583  0
                 return EOQualifierSQLGeneration.Support.supportForClass(EOKeyComparisonQualifier.class).sqlStringForSQLExpression(q, this);
 584  
         }
 585  
 
 586  
         public String sqlStringForKeyValueQualifier(EOKeyValueQualifier q) {
 587  0
                 return EOQualifierSQLGeneration.Support.supportForClass(EOKeyValueQualifier.class).sqlStringForSQLExpression(q, this);
 588  
         }
 589  
 
 590  
         public String sqlStringForNegatedQualifier(EOQualifier q) {
 591  0
                 EOQualifierSQLGeneration.Support sup = EOQualifierSQLGeneration.Support.supportForClass(q.getClass());
 592  0
                 String sql = sup.sqlStringForSQLExpression(q, this);
 593  0
                 return "NOT (" + sql + ")";
 594  
         }
 595  
 
 596  
         public static String sqlStringForNumber(Number number) {
 597  0
                 return number.toString();
 598  
         }
 599  
 
 600  
         public String sqlStringForQualifier(EOQualifierSQLGeneration sql) {
 601  0
                 return sql.sqlStringForSQLExpression(this);
 602  
         }
 603  
 
 604  
         public String sqlStringForSchemaObjectName(String name) {
 605  0
                 return name;
 606  
         }
 607  
 
 608  
         public String sqlStringForSelector(NSSelector sel, Object value) {
 609  0
                 if (sel == EOQualifier.QualifierOperatorEqual) {
 610  0
                         if (value == NSKeyValueCoding.NullValue)
 611  0
                                 return " is ";
 612  0
                         return "=";
 613  0
                 } else if (sel == EOQualifier.QualifierOperatorNotEqual) {
 614  0
                         if (value == NSKeyValueCoding.NullValue)
 615  0
                                 return " is not ";
 616  0
                         return "<>";
 617  0
                 } else if (sel == EOQualifier.QualifierOperatorLessThan) {
 618  0
                         return "<";
 619  0
                 } else if (sel == EOQualifier.QualifierOperatorGreaterThan) {
 620  0
                         return ">";
 621  0
                 } else if (sel == EOQualifier.QualifierOperatorLessThanOrEqualTo) {
 622  0
                         return "<=";
 623  0
                 } else if (sel == EOQualifier.QualifierOperatorGreaterThanOrEqualTo) {
 624  0
                         return ">=";
 625  0
                 } else if (sel == EOQualifier.QualifierOperatorLike || sel == EOQualifier.QualifierOperatorCaseInsensitiveLike) {
 626  0
                         return " like ";
 627  
                 }
 628  0
                 return sel.name();
 629  
         }
 630  
 
 631  
         public static String sqlStringForString(String s) {
 632  0
                 return s;
 633  
         }
 634  
 
 635  
         public String sqlStringForValue(Object value, String keyPath) {
 636  0
                 EOAttribute a = _entity._attributeForPath(keyPath);
 637  0
                 return formatValueForAttribute(value, a);
 638  
         }
 639  
 
 640  
         public String tableListWithRootEntity(EOEntity root) {
 641  0
                 StringBuffer buf = new StringBuffer(root.externalName());
 642  0
                 if (useAliases()) {
 643  0
                         buf.append(" ");
 644  0
                         buf.append(_aliasesByEntityName.objectForKey(root.name()));
 645  
                 }
 646  0
                 if (_aliasesByEntityName.count() > 0) {
 647  0
                         Enumeration enumeration = _aliasesByEntityName.keyEnumerator();
 648  0
                         while (enumeration.hasMoreElements()) {
 649  0
                                 String key = (String)enumeration.nextElement();
 650  0
                                 if (!key.equals(root.name())) {
 651  0
                                         buf.append(", ");
 652  0
                                         buf.append(key);
 653  0
                                         if (useAliases())
 654  0
                                                 buf.append(_aliasesByEntityName.objectForKey(key));
 655  
                                 }
 656  0
                         }
 657  
                 }
 658  0
                 return buf.toString();
 659  
         }
 660  
 
 661  
         public String toString() {
 662  0
                 return "<" + getClass().getName() + "> " + statement();
 663  
         }
 664  
 
 665  
         public String valueList() {
 666  0
                 return _valueList().toString();
 667  
         }
 668  
 
 669  
 }
 670  
 /*
 671  
  * $Log$
 672  
  * Revision 1.2  2006/02/16 16:47:14  cgruber
 673  
  * Move some classes in to "internal" packages and re-work imports, etc.
 674  
  *
 675  
  * Also use UnsupportedOperationExceptions where appropriate, instead of WotonomyExceptions.
 676  
  *
 677  
  * Revision 1.1  2006/02/16 13:19:57  cgruber
 678  
  * Check in all sources in eclipse-friendly maven-enabled packages.
 679  
  *
 680  
  * Revision 1.5  2005/05/11 15:21:53  cgruber
 681  
  * Change enum to enumeration, since enum is now a keyword as of Java 5.0
 682  
  *
 683  
  * A few other comments in the code.
 684  
  *
 685  
  * Revision 1.4  2003/08/29 21:14:18  chochos
 686  
  * fix the algorithm in formatStringValue.
 687  
  *
 688  
  * Revision 1.3  2003/08/14 02:12:32  chochos
 689  
  * implemented use of (simple) qualifiers
 690  
  *
 691  
  * Revision 1.2  2003/08/13 22:59:39  chochos
 692  
  * Can now generate simple one-entity select statements.
 693  
  *
 694  
  * Revision 1.1  2003/08/13 01:04:32  chochos
 695  
  * the SQL generation classes. EOSQLExpression still needs a lot of work, but the factory is pretty much done.
 696  
  *
 697  
  */