TransWikia.com

chainbase::database error

EOS.IO Asked by iambaeba1 on August 20, 2021

After program is terminated, user defined object cannot be loaded to chainbase::database.

my code is followed.

enum my_type {
    my_inx01_object_type
};

namespace eosio { namespace chain {
    using boost::multi_index_container;
    using namespace boost::multi_index;

    class my_inx01_object : public chainbase::object<my_inx01_object_type, my_inx01_object> {
        OBJECT_CTOR(my_inx01_object)
        id_type     id;
        string      action_sign;
        string      trx_id;
    };

    struct by_sign;
    using my_inx01_index = chainbase::shared_multi_index_container<
        my_inx01_object,
        indexed_by<
            ordered_unique< 
                tag<by_id>, 
                member<my_inx01_object, my_inx01_object::id_type, &my_inx01_object::id>
            >,
            ordered_unique< 
                tag<by_sign>, 
                BOOST_MULTI_INDEX_MEMBER(my_inx01_object, string, action_sign) 
            >
        >
    >;
} } // End of namespace eosio::chain
CHAINBASE_SET_INDEX_TYPE(eosio::chain::my_inx01_object, eosio::chain::my_inx01_index)
FC_REFLECT(eosio::chain::my_inx01_object, (action_sign)(trx_id))

void internal_db_test3()
{
    uint32_t nRet;

    chainbase::database db(
        "/home/my/Documents/default_boot/blockchain_debug/data/",
        database::read_write, //database::read_only,
        1024*1024*1);   // 1 mb
    
    db.add_index< my_inx01_index >();
    
    // insert   
    string strTrxId = "TRXID0000000000000000000000000000000000000000000000000000000001";
    string strActionSign = "SIGNP0123456789012345678901234567890123456789012345678901234567";

    // select
    const my_inx01_object *result = db.find<my_inx01_object, by_sign>(strActionSign);

    db.create<my_inx01_object>(
        [&](auto &a) {
            a.action_sign = strActionSign;
            a.trx_id = strTrxId;
        }
    );
    
    // select
    const my_inx01_object *result2 = db.find<my_inx01_object, by_sign>(strActionSign);
}

void internal_db_test4()
{
    uint32_t nRet;

    chainbase::database db(
        "/home/my/Documents/default_boot/blockchain_debug/data/",
        database::read_write, //database::read_only,
        1024*1024*1);   // 1 mb
    
    db.add_index< my_inx01_index >();
    
    // insert   
    string strTrxId = "TRXID0000000000000000000000000000000000000000000000000000000001";
    string strActionSign = "SIGNP0123456789012345678901234567890123456789012345678901234567";

    // select
    const my_inx01_object *result = db.find<my_inx01_object, by_sign>(strActionSign);
}

int main(int argc, char** argv)
{
    internal_db_test3();
    internal_db_test4();
   return 1;
}

Above code is not problem that execute once. internal_db_test3() and internal_db_test4() are ok.

Code is modified and the program is restarted

int main(int argc, char** argv)
{
    //internal_db_test3();
    internal_db_test4();
   return 1;
}

// select
    const my_inx01_object *result = db.find<my_inx01_object, by_sign>(strActionSign);
    ==> result is null !!

But I don’t understand why result is null.

One Answer

I found the solution. The reference code is followed by boost manual. (https://www.boost.org/doc/libs/1_73_0/libs/multi_index/example/ip_allocator.cpp)

Boost.MultiIndex supports special allocators such as those provided by Boost.Interprocess, which allows for multi_index_containers to be placed in shared memory.

Chainbase database use shared memory. If user defined object has string type, string type must be changed to shared_string type.

namespace eosio { namespace chain {
    using boost::multi_index_container;
    using namespace boost::multi_index;

    class my_inx02_object : public chainbase::object<my_inx02_object_type, my_inx02_object> {
        OBJECT_CTOR(my_inx02_object, (action_sign)(trx_id))
        id_type             id;
        shared_string       action_sign;
        shared_string       trx_id;
    };

    struct by_sign;
    using my_inx02_index = chainbase::shared_multi_index_container<
        my_inx02_object,
        indexed_by<
            ordered_unique< 
                tag<by_id>, 
                member<my_inx02_object, my_inx02_object::id_type, &my_inx02_object::id>
            >,
            ordered_unique< 
                tag<by_sign>, 
                BOOST_MULTI_INDEX_MEMBER(my_inx02_object, shared_string, action_sign)           
            >
        >
    >;
} } // End of namespace eosio::chain
CHAINBASE_SET_INDEX_TYPE(eosio::chain::my_inx02_object, eosio::chain::my_inx02_index)
FC_REFLECT(eosio::chain::my_inx02_object, (action_sign)(trx_id))

void internal_db_test5()
{
    chainbase::database db(
        "/home/my/Documents/default_boot/blockchain_debug/data/",
        database::read_write, //database::read_only,
        1024*1024*1);   // 1 mb

    db.add_index< my_inx02_index >();

    string strTrxId = "TRXID0000000000000000000000000000000000000000000000000000000001";
    string strActionSign = "SIGNP0123456789012345678901234567890123456789012345678901234567";
    
    shared_string ssActionSign( shared_string::allocator_type(db.get_segment_manager()) );
    ssActionSign.assign(strActionSign.c_str(), strActionSign.length());

    // select
    const my_inx02_object *result = db.find<my_inx02_object, by_sign>(ssActionSign);

    if ( result != nullptr) {
        string strData_action_sign = result->action_sign.data();
        string strData_TrxId = result->trx_id.data();
    }

    db.create<my_inx02_object>(
        [&](auto &a) {
            a.action_sign.assign( strActionSign.c_str(), strActionSign.length() );
            a.trx_id.assign( strTrxId.c_str(), strTrxId.length() );
        }
    );

    // select
    const my_inx02_object *result2 = db.find<my_inx02_object, by_sign>(ssActionSign);
}

int main(int argc, char** argv)
{
   internal_db_test5();
   return 1;
}

After the program is shutdowned and restarted, you can successfuly access shared_string types.

Answered by iambaeba1 on August 20, 2021

Add your own answers!

Ask a Question

Get help from others!

© 2024 TransWikia.com. All rights reserved. Sites we Love: PCI Database, UKBizDB, Menu Kuliner, Sharing RPP