示例#1
0
 ResultTempTable(Session session, Expression[] expressions, boolean distinct, SortOrder sort) {
   this.session = session;
   this.distinct = distinct;
   this.sort = sort;
   this.columnCount = expressions.length;
   Schema schema = session.getDatabase().getSchema(Constants.SCHEMA_MAIN);
   CreateTableData data = new CreateTableData();
   for (int i = 0; i < expressions.length; i++) {
     int type = expressions[i].getType();
     Column col = new Column(COLUMN_NAME + i, type);
     if (type == Value.CLOB || type == Value.BLOB) {
       containsLob = true;
     }
     data.columns.add(col);
   }
   data.id = session.getDatabase().allocateObjectId();
   data.tableName = "TEMP_RESULT_SET_" + data.id;
   data.temporary = true;
   data.persistIndexes = false;
   data.persistData = true;
   data.create = true;
   data.session = session;
   table = schema.createTable(data);
   if (sort != null || distinct) {
     createIndex();
   }
   parent = null;
 }
示例#2
0
 /**
  * Construct a new row list for this session.
  *
  * @param session the session
  */
 public RowList(Session session) {
   this.session = session;
   if (session.getDatabase().isPersistent()) {
     maxMemory = session.getDatabase().getMaxOperationMemory();
   } else {
     maxMemory = 0;
   }
 }
示例#3
0
 private void createIndex() {
   IndexColumn[] indexCols = null;
   if (sort != null) {
     int[] colIndex = sort.getQueryColumnIndexes();
     indexCols = new IndexColumn[colIndex.length];
     for (int i = 0; i < colIndex.length; i++) {
       IndexColumn indexColumn = new IndexColumn();
       indexColumn.column = table.getColumn(colIndex[i]);
       indexColumn.sortType = sort.getSortTypes()[i];
       indexColumn.columnName = COLUMN_NAME + i;
       indexCols[i] = indexColumn;
     }
   } else {
     indexCols = new IndexColumn[columnCount];
     for (int i = 0; i < columnCount; i++) {
       IndexColumn indexColumn = new IndexColumn();
       indexColumn.column = table.getColumn(i);
       indexColumn.columnName = COLUMN_NAME + i;
       indexCols[i] = indexColumn;
     }
   }
   String indexName = table.getSchema().getUniqueIndexName(session, table, Constants.PREFIX_INDEX);
   int indexId = session.getDatabase().allocateObjectId();
   IndexType indexType = IndexType.createNonUnique(true);
   index = table.addIndex(session, indexName, indexId, indexCols, indexType, true, null);
 }
示例#4
0
 @Override
 public Value[] next() {
   if (resultCursor == null) {
     Index idx;
     if (distinct || sort != null) {
       idx = index;
     } else {
       idx = table.getScanIndex(session);
     }
     if (session.getDatabase().getMvStore() != null) {
       // sometimes the transaction is already committed,
       // in which case we can't use the session
       if (idx.getRowCount(session) == 0 && rowCount > 0) {
         // this means querying is not transactional
         resultCursor = idx.find((Session) null, null, null);
       } else {
         // the transaction is still open
         resultCursor = idx.find(session, null, null);
       }
     } else {
       resultCursor = idx.find(session, null, null);
     }
   }
   if (!resultCursor.next()) {
     return null;
   }
   Row row = resultCursor.get();
   return row.getValueList();
 }
示例#5
0
 private boolean sameResultAsLast(Session s, Value[] params, Value[] lastParams, long lastEval) {
   if (!cacheableChecked) {
     long max = getMaxDataModificationId();
     noCache = max == Long.MAX_VALUE;
     cacheableChecked = true;
   }
   if (noCache) {
     return false;
   }
   Database db = s.getDatabase();
   for (int i = 0; i < params.length; i++) {
     Value a = lastParams[i], b = params[i];
     if (a.getType() != b.getType() || !db.areEqual(a, b)) {
       return false;
     }
   }
   if (!isEverything(ExpressionVisitor.DETERMINISTIC_VISITOR)
       || !isEverything(ExpressionVisitor.INDEPENDENT_VISITOR)) {
     return false;
   }
   if (db.getModificationDataId() > lastEval && getMaxDataModificationId() > lastEval) {
     return false;
   }
   return true;
 }
示例#6
0
 private void writeAllRows() {
   if (file == null) {
     Database db = session.getDatabase();
     String fileName = db.createTempFile();
     file = db.openFile(fileName, "rw", false);
     file.setCheckedWriting(false);
     file.seek(FileStore.HEADER_LENGTH);
     rowBuff = Data.create(db, Constants.DEFAULT_PAGE_SIZE);
     file.seek(FileStore.HEADER_LENGTH);
   }
   Data buff = rowBuff;
   initBuffer(buff);
   for (int i = 0, size = list.size(); i < size; i++) {
     if (i > 0 && buff.length() > Constants.IO_BUFFER_SIZE) {
       flushBuffer(buff);
       initBuffer(buff);
     }
     Row r = list.get(i);
     writeRow(buff, r);
   }
   flushBuffer(buff);
   file.autoDelete();
   list.clear();
   memory = 0;
 }
 @Override
 public Expression[] getExpressionColumns(Session session) {
   ExpressionColumn[] expr = new ExpressionColumn[list.length];
   for (int i = 0; i < list.length; i++) {
     Expression e = list[i];
     Column col =
         new Column(
             "C" + (i + 1), e.getType(), e.getPrecision(), e.getScale(), e.getDisplaySize());
     expr[i] = new ExpressionColumn(session.getDatabase(), col);
   }
   return expr;
 }
 public void createIndexConditions(Session session, TableFilter filter) {
   if (!(this.left instanceof ExpressionColumn)) {
     return;
   }
   ExpressionColumn l = (ExpressionColumn) this.left;
   if (filter != l.getTableFilter()) {
     return;
   }
   if (session.getDatabase().getSettings().optimizeInList) {
     filter.addIndexCondition(IndexCondition.getInList(l, this.valueList));
     return;
   }
 }
示例#9
0
 /**
  * Create a temporary view out of the given query.
  *
  * @param session the session
  * @param owner the owner of the query
  * @param name the view name
  * @param query the query
  * @param topQuery the top level query
  * @return the view table
  */
 public static TableView createTempView(
     Session session, User owner, String name, Query query, Query topQuery) {
   Schema mainSchema = session.getDatabase().getSchema(Constants.SCHEMA_MAIN);
   String querySQL = query.getPlanSQL();
   TableView v =
       new TableView(mainSchema, 0, name, querySQL, query.getParameters(), null, session, false);
   v.setTopQuery(topQuery);
   if (v.createException != null) {
     throw v.createException;
   }
   v.setOwner(owner);
   v.setTemporary(true);
   return v;
 }
示例#10
0
 private void dropTable() {
   if (table == null) {
     return;
   }
   if (containsLob) {
     // contains BLOB or CLOB: can not truncate now,
     // otherwise the BLOB and CLOB entries are removed
     return;
   }
   try {
     Database database = session.getDatabase();
     // Need to lock because not all of the code-paths
     // that reach here have already taken this lock,
     // notably via the close() paths.
     synchronized (session) {
       synchronized (database) {
         table.truncate(session);
       }
     }
     // This session may not lock the sys table (except if it already has
     // locked it) because it must be committed immediately, otherwise
     // other threads can not access the sys table. If the table is not
     // removed now, it will be when the database is opened the next
     // time. (the table is truncated, so this is just one record)
     if (!database.isSysTableLocked()) {
       Session sysSession = database.getSystemSession();
       table.removeChildrenAndResources(sysSession);
       if (index != null) {
         // need to explicitly do this,
         // as it's not registered in the system session
         session.removeLocalTempTableIndex(index);
       }
       // the transaction must be committed immediately
       // TODO this synchronization cascade is very ugly
       synchronized (session) {
         synchronized (sysSession) {
           synchronized (database) {
             sysSession.commit(false);
           }
         }
       }
     }
   } finally {
     table = null;
   }
 }
 ResultDiskBuffer(Session session, SortOrder sort, int columnCount) {
   this.parent = null;
   this.sort = sort;
   this.columnCount = columnCount;
   Database db = session.getDatabase();
   rowBuff = Data.create(db, Constants.DEFAULT_PAGE_SIZE);
   String fileName = db.createTempFile();
   file = db.openFile(fileName, "rw", false);
   file.setCheckedWriting(false);
   file.seek(FileStore.HEADER_LENGTH);
   if (sort != null) {
     tapes = New.arrayList();
     mainTape = null;
   } else {
     tapes = null;
     mainTape = new ResultDiskTape();
     mainTape.pos = FileStore.HEADER_LENGTH;
   }
   this.maxBufferSize = db.getSettings().largeResultBufferSize;
 }
示例#12
0
 @Override
 public void createIndexConditions(Session session, TableFilter filter) {
   if (!(left instanceof ExpressionColumn)) {
     return;
   }
   ExpressionColumn l = (ExpressionColumn) left;
   if (filter != l.getTableFilter()) {
     return;
   }
   if (session.getDatabase().getSettings().optimizeInList) {
     ExpressionVisitor visitor = ExpressionVisitor.getNotFromResolverVisitor(filter);
     for (Expression e : valueList) {
       if (!e.isEverything(visitor)) {
         return;
       }
     }
     filter.addIndexCondition(IndexCondition.getInList(l, valueList));
     return;
   }
 }
示例#13
0
  /**
   * @param conn Connection.
   * @param qry Query.
   * @param explain Explain.
   * @return Table.
   * @throws IgniteCheckedException
   */
  private GridMergeTable createMergeTable(
      JdbcConnection conn, GridCacheSqlQuery qry, boolean explain) throws IgniteCheckedException {
    try {
      Session ses = (Session) conn.getSession();

      CreateTableData data = new CreateTableData();

      data.tableName = "T___";
      data.schema = ses.getDatabase().getSchema(ses.getCurrentSchemaName());
      data.create = true;

      if (!explain) {
        LinkedHashMap<String, ?> colsMap = qry.columns();

        assert colsMap != null;

        ArrayList<Column> cols = new ArrayList<>(colsMap.size());

        for (Map.Entry<String, ?> e : colsMap.entrySet()) {
          String alias = e.getKey();
          GridSqlType t = (GridSqlType) e.getValue();

          assert !F.isEmpty(alias);

          Column c = new Column(alias, t.type(), t.precision(), t.scale(), t.displaySize());

          cols.add(c);
        }

        data.columns = cols;
      } else data.columns = planColumns();

      return new GridMergeTable(data, ctx);
    } catch (Exception e) {
      U.closeQuiet(conn);

      throw new IgniteCheckedException(e);
    }
  }
示例#14
0
 private Cursor find(Row row) {
   if (index == null) {
     // for the case "in(select ...)", the query might
     // use an optimization and not create the index
     // up front
     createIndex();
   }
   Cursor cursor = index.find(session, row, row);
   while (cursor.next()) {
     SearchRow found = cursor.getSearchRow();
     boolean ok = true;
     Database db = session.getDatabase();
     for (int i = 0; i < row.getColumnCount(); i++) {
       if (!db.areEqual(row.getValue(i), found.getValue(i))) {
         ok = false;
         break;
       }
     }
     if (ok) {
       return cursor;
     }
   }
   return null;
 }
示例#15
0
 public void remove(Session session) throws SQLException {
   mainIndex.setMainIndexColumn(-1);
   session.getDatabase().getPageStore().removeMeta(this, session);
 }
示例#16
0
 /**
  * Initialize the order by list. This call may extend the expressions list.
  *
  * @param session the session
  * @param expressions the select list expressions
  * @param expressionSQL the select list SQL snippets
  * @param orderList the order by list
  * @param visible the number of visible columns in the select list
  * @param mustBeInResult all order by expressions must be in the select list
  * @param filters the table filters
  */
 static void initOrder(
     Session session,
     ArrayList<Expression> expressions,
     ArrayList<String> expressionSQL,
     ArrayList<SelectOrderBy> orderList,
     int visible,
     boolean mustBeInResult,
     ArrayList<TableFilter> filters) {
   Database db = session.getDatabase();
   for (SelectOrderBy o : orderList) {
     Expression e = o.expression;
     if (e == null) {
       continue;
     }
     // special case: SELECT 1 AS A FROM DUAL ORDER BY A
     // (oracle supports it, but only in order by, not in group by and
     // not in having):
     // SELECT 1 AS A FROM DUAL ORDER BY -A
     boolean isAlias = false;
     int idx = expressions.size();
     if (e instanceof ExpressionColumn) {
       // order by expression
       ExpressionColumn exprCol = (ExpressionColumn) e;
       String tableAlias = exprCol.getOriginalTableAliasName();
       String col = exprCol.getOriginalColumnName();
       for (int j = 0; j < visible; j++) {
         boolean found = false;
         Expression ec = expressions.get(j);
         if (ec instanceof ExpressionColumn) {
           // select expression
           ExpressionColumn c = (ExpressionColumn) ec;
           found = db.equalsIdentifiers(col, c.getColumnName());
           if (found && tableAlias != null) {
             String ca = c.getOriginalTableAliasName();
             if (ca == null) {
               found = false;
               if (filters != null) {
                 // select id from test order by test.id
                 for (int i = 0, size = filters.size(); i < size; i++) {
                   TableFilter f = filters.get(i);
                   if (db.equalsIdentifiers(f.getTableAlias(), tableAlias)) {
                     found = true;
                     break;
                   }
                 }
               }
             } else {
               found = db.equalsIdentifiers(ca, tableAlias);
             }
           }
         } else if (!(ec instanceof Alias)) {
           continue;
         } else if (tableAlias == null && db.equalsIdentifiers(col, ec.getAlias())) {
           found = true;
         } else {
           Expression ec2 = ec.getNonAliasExpression();
           if (ec2 instanceof ExpressionColumn) {
             ExpressionColumn c2 = (ExpressionColumn) ec2;
             String ta = exprCol.getSQL();
             String tb = c2.getSQL();
             String s2 = c2.getColumnName();
             found = db.equalsIdentifiers(col, s2);
             if (!db.equalsIdentifiers(ta, tb)) {
               found = false;
             }
           }
         }
         if (found) {
           idx = j;
           isAlias = true;
           break;
         }
       }
     } else {
       String s = e.getSQL();
       if (expressionSQL != null) {
         for (int j = 0, size = expressionSQL.size(); j < size; j++) {
           String s2 = expressionSQL.get(j);
           if (db.equalsIdentifiers(s2, s)) {
             idx = j;
             isAlias = true;
             break;
           }
         }
       }
     }
     if (!isAlias) {
       if (mustBeInResult) {
         throw DbException.get(ErrorCode.ORDER_BY_NOT_IN_RESULT, e.getSQL());
       }
       expressions.add(e);
       String sql = e.getSQL();
       expressionSQL.add(sql);
     }
     o.columnIndexExpr = ValueExpression.get(ValueInt.get(idx + 1));
     Expression expr = expressions.get(idx).getNonAliasExpression();
     o.expression = expr;
   }
 }