예제 #1
0
void DbService::insertContract(const BfContractData& bfItem)
{
    BfDebug(__FUNCTION__);
    g_sm->checkCurrentOn(ServiceMgr::DB);

    if (bfItem.symbol().length() == 0 || bfItem.exchange().length() == 0 || bfItem.name().length() == 0) {
        BfDebug("invalid contract,ignore");
        return;
    }

    leveldb::WriteOptions options;
    leveldb::WriteBatch batch;
    std::string key, val;

    if (1) {

        // key: contract-symbol-exchange
        key = QString().sprintf("contract-%s-%s", bfItem.symbol().c_str(), bfItem.exchange().c_str()).toStdString();
        bool ok = bfItem.SerializeToString(&val);
        if (!ok) {
            qFatal("SerializeToString fail");
        }
        batch.Put(key, val);

        // key: tick-symbol-exchange+
        // key: tick-symbol-exchange=
        BfTickData bfNullTick;
        key = QString().sprintf("tick-%s-%s+", bfItem.symbol().c_str(), bfItem.exchange().c_str()).toStdString();
        val = bfNullTick.SerializeAsString();
        batch.Put(key, val);
        key = QString().sprintf("tick-%s-%s=", bfItem.symbol().c_str(), bfItem.exchange().c_str()).toStdString();
        val = bfNullTick.SerializeAsString();
        batch.Put(key, val);

        // key: bar-symbol-exchange-period+
        // key: bar-symbol-exchange-period=
        BfBarData bfNullBar;
        for (int i = BfBarPeriod_MIN; i <= BfBarPeriod_MAX; i++) {
            key = QString().sprintf("bar-%s-%s-%s+", bfItem.symbol().c_str(), bfItem.exchange().c_str(), qPrintable(ProtoUtils::formatPeriod((BfBarPeriod)i))).toStdString();
            val = bfNullBar.SerializeAsString();
            batch.Put(key, val);
            key = QString().sprintf("bar-%s-%s-%s=", bfItem.symbol().c_str(), bfItem.exchange().c_str(), qPrintable(ProtoUtils::formatPeriod((BfBarPeriod)i))).toStdString();
            val = bfNullBar.SerializeAsString();
            batch.Put(key, val);
        }
    }

    db_->Write(options, &batch);
}
예제 #2
0
void DbService::getTick(const BfGetTickReq* request, ::grpc::ServerWriter<BfTickData>* writer)
{
    g_sm->checkCurrentOn(ServiceMgr::EXTERNAL);

    if (request->symbol().length() == 0 || request->exchange().length() == 0 || request->todate().length() == 0 || request->totime().length() == 0) {
        BfDebug("invalid parm,ignore");
        return;
    }

    leveldb::ReadOptions options;
    options.fill_cache = false;
    leveldb::Iterator* it = db_->NewIterator(options);
    if (!it) {
        qFatal("NewIterator == nullptr");
    }

    // key: tick-symbol-exchange-actiondate-ticktime
    std::string key = QString().sprintf("tick-%s-%s-%s-%s", request->symbol().c_str(), request->exchange().c_str(), request->todate().c_str(), request->totime().c_str()).toStdString();
    it->Seek(leveldb::Slice(key));
    int count = 0;
    for (; it->Valid() && count < request->count(); it->Prev()) {
        //遇到了前后两个结束item
        const char* buf = it->value().data();
        int len = it->value().size();
        BfTickData bfItem;
        if (!bfItem.ParseFromArray(buf, len)) {
            qFatal("ParseFromArray error");
            break;
        }
        if (bfItem.symbol().length() == 0) {
            std::string lastestKey = QString().sprintf("tick-%s-%s=", request->symbol().c_str(), request->exchange().c_str()).toStdString();
            std::string itKey = it->key().ToString();
            if (itKey == lastestKey) {
                continue;
            } else {
                break;
            }
        }

        count++;
        writer->Write(bfItem);
    }
    delete it;
}
예제 #3
0
void DbService::batchWriteTicks()
{
    g_sm->checkCurrentOn(ServiceMgr::DB);

    if( tickCount_ == 0 ){
        return;
    }

    leveldb::WriteOptions options;
    leveldb::WriteBatch batch;
    for (int i = 0; i < tickCount_; i++) {
        void* curTick = tickArray[i].curTick;
        void* preTick = tickArray[i].preTick;

        BfTickData bfItem;
        CtpUtils::translateTick(curTick, preTick, &bfItem);

        // tick里面的exchange不一定有=
        QString exchange = bfItem.exchange().c_str();
        if (exchange.trimmed().length() == 0) {
            void* contract = g_sm->ctpMgr()->getContract(bfItem.symbol().c_str());
            exchange = CtpUtils::getExchangeFromContract(contract);
            bfItem.set_exchange(exchange.toStdString());
        }

        // key: tick.exchange.symbol.actiondata.ticktime
        std::string key = QString().sprintf("tick.%s.%s.%s.%s", bfItem.exchange().c_str(), bfItem.symbol().c_str(), bfItem.actiondate().c_str(), bfItem.ticktime().c_str()).toStdString();
        std::string val = bfItem.SerializeAsString();

        batch.Put(key, val);
    }
    db_->Write(options, &batch);

    tickCount_ = 0;
}
예제 #4
0
void DbService::insertTick(const BfTickData& bfItem)
{
    //BfDebug(__FUNCTION__);
    g_sm->checkCurrentOn(ServiceMgr::DB);

    if (bfItem.symbol().length() == 0 || bfItem.exchange().length() == 0 || bfItem.actiondate().length() == 0 || bfItem.ticktime().length() == 0) {
        BfDebug("invalid tick,ignore");
        return;
    }

    leveldb::WriteOptions options;
    leveldb::WriteBatch batch;
    std::string key, val;

    if (1) {
        // key: tick-symbol-exchange-actiondate-ticktime
        key = QString().sprintf("tick-%s-%s-%s-%s", bfItem.symbol().c_str(), bfItem.exchange().c_str(), bfItem.actiondate().c_str(), bfItem.ticktime().c_str()).toStdString();
        bool ok = bfItem.SerializeToString(&val);
        if (!ok) {
            qFatal("SerializeToString fail");
        }
        batch.Put(key, val);
    }

    db_->Write(options, &batch);
}
예제 #5
0
void PushService::onGotTick(void* curTick, void* preTick)
{
    g_sm->checkCurrentOn(ServiceMgr::PUSH);

    BfTickData data;
    CtpUtils::translateTick(curTick, preTick, &data);

    // tick里面的exchange不一定有=
    QString exchange = data.exchange().c_str();
    if (exchange.trimmed().length() == 0) {
        void* contract = g_sm->gatewayMgr()->getContract(data.symbol().c_str());
        exchange = CtpUtils::getExchangeFromContract(contract);
        data.set_exchange(exchange.toStdString());
    }

    for (auto client : clients_) {
        if (client->tickHandler() && client->subscribled(data.symbol(), data.exchange())) {
            client->OnTick(data);
        }
    }
}
예제 #6
0
파일: statform.cpp 프로젝트: flatM/bftrader
void StatForm::statTick(QString symbol, QString exchange, QString name)
{
    QString startDate, startTime, endDate, endTime;

    if (1) {
        leveldb::DB* db = g_sm->dbService()->getDb();
        leveldb::ReadOptions options;
        options.fill_cache = false;
        leveldb::Iterator* it = db->NewIterator(options);
        if (!it) {
            qFatal("NewIterator == nullptr");
        }

        //第一个是tick-symbol-exchange+
        //最后一个是tick-symbol-exchange=
        QString key = QString().sprintf("tick-%s-%s+", qPrintable(symbol), qPrintable(exchange));
        it->Seek(leveldb::Slice(key.toStdString()));
        if (it->Valid()) {
            it->Next();
        }
        if (it->Valid()) {
            //遇到了前后两个结束item
            const char* buf = it->value().data();
            int len = it->value().size();
            BfTickData bfItem;
            if (bfItem.ParseFromArray(buf, len) && bfItem.symbol().length() != 0) {
                startDate = bfItem.actiondate().c_str();
                startTime = bfItem.ticktime().c_str();
            }
        }
        delete it;
    }

    if (startDate.length() != 0) {
        leveldb::DB* db = g_sm->dbService()->getDb();
        leveldb::ReadOptions options;
        options.fill_cache = false;
        leveldb::Iterator* it = db->NewIterator(options);
        if (!it) {
            qFatal("NewIterator == nullptr");
        }

        //第一个是tick-symbol-exchange+
        //最后一个是tick-symbol-exchange=
        QString key = QString().sprintf("tick-%s-%s=", qPrintable(symbol), qPrintable(exchange));
        it->Seek(leveldb::Slice(key.toStdString()));
        if (it->Valid()) {
            it->Prev();
        }
        if (it->Valid()) {
            //遇到了前后两个结束item
            const char* buf = it->value().data();
            int len = it->value().size();
            BfTickData bfItem;
            if (bfItem.ParseFromArray(buf, len) && bfItem.symbol().length() != 0) {
                endDate = bfItem.actiondate().c_str();
                endTime = bfItem.ticktime().c_str();
            }
        }
        delete it;
    }

    if (startDate.length() != 0 && endDate.length() != 0) {
        onGotData(symbol, exchange, name, "tick", startDate, startTime, endDate, endTime);
    }
}
예제 #7
0
// 如果不是上期所,平今仓可用close或closeToday,平昨仓可用close或closeYesterday=
// 如果是上期所,平今仓只可用closeToday,平昨仓可用close或closeYesterday=
// 那成交回报的流水回来的时侯:
// CloseYesterday=> insert =>CloseYesterday
// CloseToday=> insert =>CloseToday
// 也存在:closeToday =>close或closeYesterday =>close的情况=
// 参考:http://www.cnblogs.com/xiaouisme/p/4654750.html
void PositionForm::on_pushButtonCloseAll_clicked()
{
    for (auto pos : positions_) {
        // 没有持仓的pass
        if (pos.position() == 0) {
            continue;
        }

        QString symbol = pos.symbol().c_str();
        QString exchange = pos.exchange().c_str();
        if (exchange.length() == 0) {
            void* contract = g_sm->gatewayMgr()->getContract(symbol);
            exchange = CtpUtils::getExchangeFromContract(contract);
        }

        // 没有订阅的pass
        if (!symbols_my_.contains(symbol)) {
            BfInfo(symbol + " not subscrible,please close byhand");
            continue;
        }

        // 取不到tick的pass,比如晚上if不开盘=
        void* tick = g_sm->gatewayMgr()->getLatestTick(symbol);
        if (!tick) {
            BfInfo(symbol + " has no tick,please close byhand");
            continue;
        }
        BfTickData bfTick;
        CtpUtils::translateTick(tick, nullptr, &bfTick);

        // 平昨=
        if (pos.ydposition() > 0) {
            // 限价单=
            BfOffset offset = OFFSET_CLOSE;
            BfPriceType priceType = PRICETYPE_LIMITPRICE;
            //TODO(hege):这里要判断是否超过了contract->maxLimit
            //TODO(hege):这里要判断昨持仓和今持仓,先平昨再平今=
            int volume = pos.ydposition();

            //空单-->最高价+多+平=
            //多单-->最低价+空+平=
            double price = bfTick.upperlimit();
            BfDirection direction = DIRECTION_LONG;
            if (pos.direction() == DIRECTION_NET || pos.direction() == DIRECTION_LONG) {
                direction = DIRECTION_SHORT;
                price = bfTick.lowerlimit();
            }

            BfSendOrderReq req;
            req.set_symbol(symbol.toStdString());
            req.set_exchange(exchange.toStdString());
            req.set_price(price);
            req.set_volume(volume);
            req.set_direction(direction);
            req.set_offset(offset);
            req.set_pricetype(priceType);

            QMetaObject::invokeMethod(g_sm->gatewayMgr(), "sendOrder", Qt::QueuedConnection, Q_ARG(BfSendOrderReq, req));
        }

        // 平今=
        if (pos.position() - pos.ydposition() > 0) {
            // 限价单=
            BfOffset offset = OFFSET_CLOSETODAY;
            BfPriceType priceType = PRICETYPE_LIMITPRICE;
            //TODO(hege):这里要判断是否超过了contract->maxLimit
            int volume = pos.position() - pos.ydposition();

            //空单-->最高价+多+平=
            //多单-->最低价+空+平=
            double price = bfTick.upperlimit();
            BfDirection direction = DIRECTION_LONG;
            if (pos.direction() == DIRECTION_NET || pos.direction() == DIRECTION_LONG) {
                direction = DIRECTION_SHORT;
                price = bfTick.lowerlimit();
            }

            BfSendOrderReq req;
            req.set_symbol(symbol.toStdString());
            req.set_exchange(exchange.toStdString());
            req.set_price(price);
            req.set_volume(volume);
            req.set_direction(direction);
            req.set_offset(offset);
            req.set_pricetype(priceType);

            QMetaObject::invokeMethod(g_sm->gatewayMgr(), "sendOrder", Qt::QueuedConnection, Q_ARG(BfSendOrderReq, req));
        }
    }
}
예제 #8
0
파일: tickform.cpp 프로젝트: flatM/bftrader
void TickForm::onGotTick(void* curTick, void* preTick)
{
    BfTickData bfTick;
    CtpUtils::translateTick(curTick, preTick, &bfTick);

    QVariantMap vItem;
    vItem.insert("symbol", bfTick.symbol().c_str());
    // tick里面的exchange不一定有=
    QString exchange = bfTick.exchange().c_str();
    if (exchange.trimmed().length() == 0) {
        void* contract = g_sm->ctpMgr()->getContract(bfTick.symbol().c_str());
        exchange = CtpUtils::getExchangeFromContract(contract);
    }
    vItem.insert("exchange", exchange);
    vItem.insert("actionDate", bfTick.actiondate().c_str());
    vItem.insert("tickTime", bfTick.ticktime().c_str());
    vItem.insert("lastPrice", bfTick.lastprice());
    vItem.insert("volume", bfTick.volume());
    vItem.insert("openInterest", bfTick.openinterest());
    vItem.insert("lastVolume", bfTick.lastvolume());

    vItem.insert("bidPrice1", bfTick.bidprice1());
    vItem.insert("askPrice1", bfTick.askprice1());
    vItem.insert("bidVolume1", bfTick.bidvolume1());
    vItem.insert("askVolume1", bfTick.askvolume1());

    vItem.insert("openPrice", bfTick.openprice());
    vItem.insert("highPrice", bfTick.highprice());
    vItem.insert("lowPrice", bfTick.lowprice());
    vItem.insert("preClosePrice", bfTick.precloseprice());
    vItem.insert("upperLimit", bfTick.upperlimit());
    vItem.insert("lowerLimit", bfTick.lowerlimit());

    //根据id找到对应的行,然后用列的text来在map里面取值设置到item里面=
    QString id = vItem.value("symbol").toString();
    int row = table_row_.value(id);
    for (int i = 0; i < table_col_.count(); i++) {
        QVariant raw_val = vItem.value(table_col_.at(i));
        QString str_val = raw_val.toString();
        if (raw_val.type() == QMetaType::Double || raw_val.type() == QMetaType::Float) {
            str_val = QString().sprintf("%6.3f", raw_val.toDouble());
        }

        QTableWidgetItem* item = new QTableWidgetItem(str_val);
        ui->tableWidget->setItem(row, i, item);
    }
}