@Override
 public void update(List<SymbolGapMap> list) {
   if (logger.isDebugEnabled()) {
     logger.debug(
         "iQuotationObserver "
             + list.get(0).getSeccode()
             + "  size = "
             + list.size()
             + "  "
             + Utils.formatTime(list.get(0).getTime())
             + " -- "
             + Utils.formatTime(list.get(list.size() - 1).getTime()));
   }
   applyQuotationGap(list);
 }
  @Override
  void startElement(String qName, Attributes attributes) throws SAXException {

    elementStack.push(qName);

    switch (QNAME.valueOf(qName)) {
      case candles:
        CandleGraph candleGraph = new CandleGraph();
        candleGraph.setPeriod(Integer.valueOf(attributes.getValue("period")));
        candleGraph.setStatus(CandleStatus.getFromValue(attributes.getValue("status")));
        candleGraph.setBoard(attributes.getValue("board"));
        candleGraph.setSeccode(attributes.getValue("seccode"));
        objectStack.push(candleGraph);
        break;

      case candle:
        Candle candle = new Candle();
        candle.setDate(Utils.parseDate(attributes.getValue("date")));
        candle.setOpen(Double.valueOf(attributes.getValue("open")));
        candle.setHigh(Double.valueOf(attributes.getValue("high")));
        candle.setLow(Double.valueOf(attributes.getValue("low")));
        candle.setClose(Double.valueOf(attributes.getValue("close")));
        candle.setVolume(Integer.valueOf(attributes.getValue("volume")));
        String oi = attributes.getValue("oi");
        if (oi != null) {
          candle.setOi(Integer.valueOf(oi));
        }
        objectStack.peek().getCandles().add(candle);
        break;
      default:
        break;
    }
  }
 @Override
 protected void setUp() throws Exception {
   candle = new Candle();
   tick1 =
       new TickTrade()
           .setQuantity(5)
           .setPrice(10.0)
           .setTime(Utils.parseDate("01.09.2015 12:15:32.010"));
   tick2 =
       new TickTrade()
           .setQuantity(10)
           .setPrice(8.5)
           .setTime(Utils.parseDate("01.09.2015 12:16:22.010"));
   tick3 =
       new TickTrade()
           .setQuantity(2)
           .setPrice(11.0)
           .setTime(Utils.parseDate("01.09.2015 12:16:30.210"));
 }
 @Test
 public void testProcessTick() {
   candle.setDate(Utils.parseDate("01.09.2015 12:15:00.000"));
   candle.processTick(tick1);
   Arrays.asList(
           PriceType.OPEN,
           PriceType.LOW,
           PriceType.HIGH,
           PriceType.CLOSE,
           PriceType.WEIGHTED_CLOSE)
       .forEach(pt -> assertTrue(candle.getPriceValueByType(pt) == tick1.getPrice()));
   candle.processTick(tick2);
   assertEquals(candle.getPriceValueByType(PriceType.OPEN), tick1.getPrice());
   assertEquals(
       candle.getPriceValueByType(PriceType.HIGH), Math.max(tick1.getPrice(), tick2.getPrice()));
   assertEquals(
       candle.getPriceValueByType(PriceType.LOW), Math.min(tick1.getPrice(), tick2.getPrice()));
   assertEquals(candle.getPriceValueByType(PriceType.CLOSE), tick2.getPrice());
   candle.processTick(tick3);
   assertEquals(candle.getPriceValueByType(PriceType.WEIGHTED_CLOSE), 10.375, 0.001); //
   assertEquals(
       candle.getPriceValueByType(PriceType.VOLUME_WEIGHTED), 9.235294117647058, 0.001); //
 }
 @Override
 public String toString() {
   return Utils.toString(this);
 }
  public void applyQuotationGap(List<SymbolGapMap> quotationGapList) {
    synchronized (this) {
      if (logger.isDebugEnabled()) {
        logger.debug("applyQuotationGap. size = " + quotationGapList.size());
      }

      for (SymbolGapMap gapMap : quotationGapList) {

        @SuppressWarnings("rawtypes")
        Class quotationclass = getClass();

        for (String attr : gapMap.keySet()) {
          Object value = null;
          String stringValue = gapMap.get(attr);

          if ("point_cost".equals(attr)
              || "open".equals(attr)
              || "waprice".equals(attr)
              || "bid".equals(attr)
              || "offer".equals(attr)
              || "last".equals(attr)
              || "change".equals(attr)
              || "priceminusprevwaprice".equals(attr)
              || "valtoday".equals(attr)
              || "yield".equals(attr)
              || "yieldatwaprice".equals(attr)
              || "marketpricetoday".equals(attr)
              || "highbid".equals(attr)
              || "lowoffer".equals(attr)
              || "high".equals(attr)
              || "low".equals(attr)
              || "closeprice".equals(attr)
              || "closeyield".equals(attr)
              || "buydeposit".equals(attr)
              || "selldeposit".equals(attr)
              || "volatility".equals(attr)
              || "theoreticalprice".equals(attr)) value = Double.valueOf(stringValue);
          else if ("accruedintvalue".equals(attr)
              || "biddepth".equals(attr)
              || "numbids".equals(attr)
              || "offerdepth".equals(attr)
              || "offerdeptht".equals(attr)
              || "numoffers".equals(attr)
              || "numtrades".equals(attr)
              || "voltoday".equals(attr)
              || "openpositions".equals(attr)
              || "deltapositions".equals(attr)
              || "quantity".equals(attr)) value = Integer.valueOf(stringValue);
          else if ("time".equals(attr) && stringValue != null && !stringValue.isEmpty()) {
            if (stringValue.length() > 12) { // определяем дату или время
              value = Utils.parseDate(stringValue);
            } else {
              value = Utils.parseTime(stringValue);
            }
          } else if ("status".equals(attr)) value = QuotationStatus.valueOf(stringValue);
          else if ("tradingstatus".equals(attr)) {
            switch (stringValue.toCharArray()[0]) {
              case '0':
              case '1':
              case '2':
              case '3':
              case '4':
                stringValue = "_" + stringValue;
            }
            value = TradingStatus.valueOf(stringValue);
          } else continue;

          try {
            Field f = quotationclass.getDeclaredField(attr);
            if (!f.isAccessible()) {
              f.setAccessible(true);
            }
            f.set(this, value);
          } catch (Exception e) {
            e.printStackTrace();
            return;
          }
        }
      }
    }
    if (quotationGapList.size() > 0 && quotationProcessingContext != null) {
      quotationProcessingContext.onQuotationsChange(new TQSymbol(board, seccode), this);
    }
  }