@Test
  public void testProcessWithOccasionalBlocks() throws Exception {
    List elements = new ArrayList();
    elements.add(new ElementSymbol("a")); // $NON-NLS-1$

    HashSet blocked =
        new HashSet(Arrays.asList(new Integer[] {new Integer(0), new Integer(2), new Integer(7)}));
    int numBatches = 10;
    int batchRow = 1;
    int rowsPerBatch = 50;
    List[] expectedResults = new List[rowsPerBatch * (numBatches - blocked.size())];
    List batches = new ArrayList();
    for (int b = 0; b < numBatches; b++) {
      if (blocked.contains(new Integer(b))) {
        batches.add(BlockedException.INSTANCE);
      } else {
        List[] rows = new List[rowsPerBatch];
        for (int i = 0; i < rowsPerBatch; i++) {
          rows[i] = new ArrayList();
          rows[i].add(new Integer(batchRow));
          expectedResults[batchRow - 1] = rows[i];
          batchRow++;
        }

        TupleBatch batch = new TupleBatch(batchRow - rows.length, rows);
        if (b == numBatches - 1) {
          batch.setTerminationFlag(true);
        }
        batches.add(batch);
      }
    }

    FakeProcessorPlan plan = new FakeProcessorPlan(elements, batches);
    helpTestProcessor(plan, expectedResults);
  }
  @Test
  public void testBlockNoResults() throws Exception {
    List elements = new ArrayList();
    elements.add(new ElementSymbol("a")); // $NON-NLS-1$

    List batches = new ArrayList();
    batches.add(BlockedException.INSTANCE);
    TupleBatch batch = new TupleBatch(1, new List[0]);
    batch.setTerminationFlag(true);
    batches.add(batch);

    FakeProcessorPlan plan = new FakeProcessorPlan(elements, batches);
    helpTestProcessor(plan, new List[0]);
  }
示例#3
0
  @Override
  protected synchronized TupleBatch nextBatchDirect()
      throws BlockedException, TeiidComponentException, TeiidProcessingException {

    evaluate(false);

    if (streaming) {
      while (state == State.BUILDING) {
        try {
          this.wait();
        } catch (InterruptedException e) {
          throw new TeiidRuntimeException(QueryPlugin.Event.TEIID30169, e);
        }
      }
      unwrapException(asynchException);
      TupleBatch batch = this.buffer.getBatch(outputRow);
      outputRow = batch.getEndRow() + 1;
      if (state != State.DONE && !batch.getTerminationFlag()) {
        state = hasNextBatch() ? State.AVAILABLE : State.BUILDING;
      }
      return batch;
    }

    while (!isBatchFull() && !isLastBatch()) {
      if (item == null) {
        try {
          item = result.iter.next();
        } catch (XPathException e) {
          throw new TeiidProcessingException(
              QueryPlugin.Event.TEIID30170,
              e,
              QueryPlugin.Util.gs(QueryPlugin.Event.TEIID30170, e.getMessage()));
        }
        rowCount++;
        if (item == null) {
          terminateBatches();
          break;
        }
      }
      addBatchRow(processRow());
      if (rowCount == rowLimit) {
        terminateBatches();
        break;
      }
    }
    return pullBatch();
  }
示例#4
0
  private void helpTestNextBatch(int tupleBatchSize, Mode mode) throws Exception {

    ProjectIntoNode node = new ProjectIntoNode(2);

    TupleSource tupleSource = new FakeDataTupleSource(NUM_ROWS);
    RelationalNode child = new FakeRelationalNode(1, tupleSource, tupleBatchSize);
    node.addChild(child);
    node.setIntoGroup(new GroupSymbol("myGroup")); // $NON-NLS-1$
    ElementSymbol elementSymbol_1 = new ElementSymbol("myGroup.myElement1"); // $NON-NLS-1$
    ElementSymbol elementSymbol_2 = new ElementSymbol("myGroup.myElement2"); // $NON-NLS-1$
    elementSymbol_1.setType(Integer.class);
    elementSymbol_2.setType(String.class);
    List<ElementSymbol> elements = Arrays.asList(elementSymbol_1, elementSymbol_2);
    node.setIntoElements(elements);
    child.setElements(elements);
    node.setMode(mode);
    node.setModelName("myModel"); // $NON-NLS-1$

    CommandContext context = new CommandContext();
    BufferManager bm = BufferManagerFactory.getTestBufferManager(tupleBatchSize, tupleBatchSize);
    ProcessorDataManager dataManager = new FakePDM(tupleBatchSize);

    child.initialize(context, bm, dataManager);
    node.initialize(context, bm, dataManager);
    node.open();

    TupleBatch batch = null;
    // Do the remaining batches
    while (true) {
      try {
        batch = node.nextBatch();
        break;
      } catch (BlockedException e) {
        // Normal
      }
    }
    assertNotNull(batch);
    List[] tuples = batch.getAllTuples();
    assertEquals(1, tuples.length);
    Object[] columns = tuples[0].toArray();
    assertNotNull(columns);
    assertEquals(1, columns.length);
    // Should have inserted all rows
    assertEquals(new Integer(NUM_ROWS), columns[0]);
  }
示例#5
0
  protected TupleBatch pullBatch() {
    TupleBatch batch = null;
    if (this.batchRows != null) {
      batch = new TupleBatch(this.beginBatch, this.batchRows);
      beginBatch += this.batchRows.size();
    } else {
      batch = new TupleBatch(this.beginBatch, Collections.EMPTY_LIST);
    }

    batch.setTerminationFlag(this.lastBatch);

    // Reset batch state
    this.batchRows = null;
    this.lastBatch = false;

    // Return batch
    return batch;
  }
示例#6
0
  /** @see ProcessorPlan#nextBatch() */
  public TupleBatch nextBatchDirect()
      throws TeiidComponentException, TeiidProcessingException, BlockedException {

    // Already returned results?
    if (done) {
      // Already returned all results
      TupleBatch emptyTerminationBatch = new TupleBatch(beginBatch, new List[0]);
      emptyTerminationBatch.setTerminationFlag(true);
      return emptyTerminationBatch;
    }
    // First attempt to process
    if (this.finalTupleSource == null) {
      // Still need to process - this should either
      // throw a BlockedException or return a finalTupleSource
      this.finalTupleSource = processProcedure();
    }

    // Next, attempt to return batches if processing completed
    while (!isBatchFull()) {
      // May throw BlockedException and exit here
      List<?> tuple = this.finalTupleSource.nextTuple();
      if (tuple == null) {
        if (outParams != null) {
          VariableContext vc = getCurrentVariableContext();
          List<Object> paramTuple = Arrays.asList(new Object[this.getOutputElements().size()]);
          int i = this.getOutputElements().size() - this.outParams.size();
          for (ElementSymbol param : outParams) {
            Object value = vc.getValue(param);
            checkNotNull(param, value);
            paramTuple.set(i++, value);
          }
          addBatchRow(paramTuple, true);
        }
        terminateBatches();
        done = true;
        break;
      }
      addBatchRow(tuple, false);
    }

    return pullBatch();
  }
示例#7
0
  /**
   * Construct a QueryResults from a TupleBatch. Take all rows from the QueryBatch and put them into
   * the QueryResults.
   *
   * @param elements List of SingleElementSymbols
   * @param tupleBatch Batch of rows
   */
  public QueryResults(List elements, TupleBatch tupleBatch) {
    // Add fields
    List columnInfos = createColumnInfos(elements);
    for (int i = 0; i < columnInfos.size(); i++) {
      ColumnInfo info = (ColumnInfo) columnInfos.get(i);
      addField(info);
    }

    // Add records in bulk -
    this.records = Arrays.asList(tupleBatch.getAllTuples());
  }
示例#8
0
  private TupleBatch nextBatchDirect()
      throws BlockedException, TeiidProcessingException, TeiidComponentException {

    boolean done = false;
    TupleBatch result = null;

    try {
      init();
      long currentTime = System.currentTimeMillis();
      Assertion.assertTrue(!processorClosed);

      // TODO: see if there is pending work before preempting

      while (currentTime < context.getTimeSliceEnd() || context.isNonBlocking()) {
        if (requestCanceled) {
          throw new TeiidProcessingException(
              QueryPlugin.Event.TEIID30160,
              QueryPlugin.Util.gs(QueryPlugin.Event.TEIID30160, getProcessID()));
        }
        if (currentTime > context.getTimeoutEnd()) {
          throw new TeiidProcessingException(
              QueryPlugin.Event.TEIID30161, QueryPlugin.Util.gs(QueryPlugin.Event.TEIID30161));
        }
        result = processPlan.nextBatch();

        if (continuous) {
          result.setRowOffset(rowOffset);

          if (result.getTerminationFlag()) {
            result.setTermination(TupleBatch.ITERATION_TERMINATED);
            List<Object> terminationTuple =
                Arrays.asList(new Object[this.getOutputElements().size()]);
            result.getTuples().add(terminationTuple);
            this.context.getTupleSourceCache().close();
            this.processPlan.close();
            this.processPlan.reset();
            this.context.incrementReuseCount();
            this.open = false;
          }

          rowOffset = result.getEndRow() + 1;
        }

        if (result.getTermination() != TupleBatch.NOT_TERMINATED) {
          if (result.getTerminationFlag()) {
            done = true;
          }
          break;
        }

        if (result.getRowCount() > 0) {
          break;
        }
      }
    } catch (BlockedException e) {
      throw e;
    } catch (TeiidException e) {
      closeProcessing();
      if (e instanceof TeiidProcessingException) {
        throw (TeiidProcessingException) e;
      }
      if (e instanceof TeiidComponentException) {
        throw (TeiidComponentException) e;
      }
      throw new TeiidComponentException(QueryPlugin.Event.TEIID30162, e);
    }
    if (done) {
      closeProcessing();
    }
    if (result == null) {
      throw EXPIRED_TIME_SLICE;
    }
    return result;
  }
示例#9
0
  /**
   * Get batch from child node Walk through each row of child batch Bind values to insertCommand
   * Execute insertCommand Update insertCount When no more data is available, output batch with
   * single row containing insertCount
   */
  public TupleBatch nextBatchDirect()
      throws BlockedException, TeiidComponentException, TeiidProcessingException {

    while (phase == REQUEST_CREATION) {

      checkExitConditions();

      /* If we don't have a batch to work, get the next
       */
      if (currentBatch == null) {
        if (sourceDone) {
          phase = RESPONSE_PROCESSING;
          break;
        }
        currentBatch = getChildren()[0].nextBatch(); // can throw BlockedException
        sourceDone = currentBatch.getTerminationFlag();
        this.batchRow = currentBatch.getBeginRow();

        // normally we would want to skip a 0 sized batch, but it typically represents the terminal
        // batch
        // and for implicit temp tables we need to issue an empty insert
        if (currentBatch.getRowCount() == 0
            && (!currentBatch.getTerminationFlag() || mode != Mode.ITERATOR)) {
          currentBatch = null;
          continue;
        }
      }

      int batchSize = currentBatch.getRowCount();
      int requests = 1;
      switch (mode) {
        case ITERATOR:
          if (buffer == null) {
            buffer =
                getBufferManager()
                    .createTupleBuffer(intoElements, getConnectionID(), TupleSourceType.PROCESSOR);
          }
          buffer.addTupleBatch(currentBatch, true);
          if (currentBatch.getTerminationFlag()
              && (buffer.getRowCount() != 0 || intoGroup.isImplicitTempGroupSymbol())) {
            Insert insert = new Insert(intoGroup, intoElements, null);
            buffer.close();
            insert.setTupleSource(buffer.createIndexedTupleSource(true));
            // Register insert command against source
            registerRequest(insert);
          } else {
            requests = 0;
          }
          break;
        case BATCH:
          // Register batched update command against source
          int endRow = currentBatch.getEndRow();
          List<Command> rows = new ArrayList<Command>(endRow - batchRow);
          for (int rowNum = batchRow; rowNum <= endRow; rowNum++) {

            Insert insert =
                new Insert(
                    intoGroup,
                    intoElements,
                    convertValuesToConstants(currentBatch.getTuple(rowNum), intoElements));
            rows.add(insert);
          }
          registerRequest(new BatchedUpdateCommand(rows));
          break;
        case SINGLE:
          batchSize = 1;
          // Register insert command against source
          // Defect 16036 - submit a new INSERT command to the DataManager.
          registerRequest(
              new Insert(
                  intoGroup,
                  intoElements,
                  convertValuesToConstants(currentBatch.getTuple(batchRow), intoElements)));
      }

      this.batchRow += batchSize;
      if (batchRow > currentBatch.getEndRow()) {
        currentBatch = null;
      }
      this.requestsRegistered += requests;
    }

    checkExitConditions();

    // End this node's work
    addBatchRow(Arrays.asList(insertCount));
    terminateBatches();
    return pullBatch();
  }