diff --git a/cosmos/poc/app/app.go b/cosmos/poc/app/app.go index 82dd545c..a70258f0 100644 --- a/cosmos/poc/app/app.go +++ b/cosmos/poc/app/app.go @@ -6,7 +6,6 @@ import ( "github.com/cosmos/cosmos-sdk/wire" "github.com/cosmos/cosmos-sdk/x/auth" "github.com/cosmos/cosmos-sdk/x/bank" - "github.com/cosmos/cosmos-sdk/x/ibc" . "github.com/cybercongress/cyberd/cosmos/poc/app/bank" . "github.com/cybercongress/cyberd/cosmos/poc/app/storage" abci "github.com/tendermint/tendermint/abci/types" @@ -25,8 +24,8 @@ type CyberdAppDbKeys struct { acc *sdk.KVStoreKey accIndex *sdk.KVStoreKey cidIndex *sdk.KVStoreKey - cidIns *sdk.KVStoreKey - cidOuts *sdk.KVStoreKey + inLinks *sdk.KVStoreKey + outLinks *sdk.KVStoreKey rank *sdk.KVStoreKey } @@ -43,14 +42,12 @@ type CyberdApp struct { // manage getting and setting accounts accStorage auth.AccountMapper - cidIndexMapper CidIndexStorage - inCidsMapper LinksStorage - outCidsMapper LinksStorage feeCollectionKeeper auth.FeeCollectionKeeper coinKeeper bank.Keeper - ibcMapper ibc.Mapper - memStorage *InMemoryStorage + // cyberd storages + persistStorages CyberdPersistentStorages + memStorage *InMemoryStorage } // NewBasecoinApp returns a reference to a new CyberdApp given a @@ -67,31 +64,36 @@ func NewCyberdApp(logger log.Logger, db dbm.DB, baseAppOptions ...func(*baseapp. main: sdk.NewKVStoreKey("main"), acc: sdk.NewKVStoreKey("acc"), cidIndex: sdk.NewKVStoreKey("cid_index"), - cidIns: sdk.NewKVStoreKey("cid_ins"), - cidOuts: sdk.NewKVStoreKey("cid_outs"), + inLinks: sdk.NewKVStoreKey("in_links"), + outLinks: sdk.NewKVStoreKey("out_links"), rank: sdk.NewKVStoreKey("rank"), } + cis := NewCidIndexStorage(dbKeys.main, dbKeys.cidIndex) + storages := CyberdPersistentStorages{ + CidIndex: cis, + InLinks: NewLinksStorage(dbKeys.inLinks, cdc), + OutLinks: NewLinksStorage(dbKeys.outLinks, cdc), + Rank: NewRankStorage(cis, dbKeys.rank), + } + // create your application type var app = &CyberdApp{ - cdc: cdc, - BaseApp: baseapp.NewBaseApp(appName, logger, db, auth.DefaultTxDecoder(cdc), baseAppOptions...), - dbKeys: dbKeys, + cdc: cdc, + BaseApp: baseapp.NewBaseApp(appName, logger, db, auth.DefaultTxDecoder(cdc), baseAppOptions...), + dbKeys: dbKeys, + persistStorages: storages, } // define and attach the mappers and keepers app.accStorage = auth.NewAccountMapper(app.cdc, dbKeys.acc, NewAccount) app.coinKeeper = bank.NewKeeper(app.accStorage) - app.cidIndexMapper = NewCidIndexStorage(dbKeys.main, dbKeys.cidIndex) - app.inCidsMapper = NewLinksStorage(dbKeys.cidIns, app.cdc) - app.outCidsMapper = NewLinksStorage(dbKeys.cidOuts, app.cdc) - - app.memStorage = NewInMemoryStorage(app.cidIndexMapper, app.inCidsMapper, app.outCidsMapper, app.accStorage) + app.memStorage = NewInMemoryStorage(storages, app.accStorage) // register message routes app.Router(). AddRoute("bank", NewBankHandler(app.coinKeeper, app.memStorage)). - AddRoute("link", NewLinksHandler(app.cidIndexMapper, app.inCidsMapper, app.outCidsMapper, app.memStorage)) + AddRoute("link", NewLinksHandler(storages.CidIndex, storages.InLinks, storages.OutLinks, app.memStorage)) // perform initialization logic app.SetInitChainer(NewGenesisApplier(app.memStorage, app.cdc, app.accStorage)) @@ -100,7 +102,7 @@ func NewCyberdApp(logger log.Logger, db dbm.DB, baseAppOptions ...func(*baseapp. app.SetAnteHandler(auth.NewAnteHandler(app.accStorage, app.feeCollectionKeeper)) // mount the multistore and load the latest state - app.MountStoresIAVL(dbKeys.main, dbKeys.acc, dbKeys.cidIndex, dbKeys.cidIns, dbKeys.cidOuts, dbKeys.rank) + app.MountStoresIAVL(dbKeys.main, dbKeys.acc, dbKeys.cidIndex, dbKeys.inLinks, dbKeys.outLinks, dbKeys.rank) err := app.LoadLatestVersion(dbKeys.main) if err != nil { cmn.Exit(err.Error()) diff --git a/cosmos/poc/app/storage/inmemory.go b/cosmos/poc/app/storage/inmemory.go index 45782fb1..65509548 100644 --- a/cosmos/poc/app/storage/inmemory.go +++ b/cosmos/poc/app/storage/inmemory.go @@ -17,21 +17,15 @@ type InMemoryStorage struct { userStake map[AccountNumber]int64 // persistent storages - cis CidIndexStorage - ils LinksStorage - ols LinksStorage - am auth.AccountMapper + persistentStorage CyberdPersistentStorages + am auth.AccountMapper } -func NewInMemoryStorage( - cis CidIndexStorage, ils LinksStorage, ols LinksStorage, am auth.AccountMapper, -) *InMemoryStorage { +func NewInMemoryStorage(persistentStorage CyberdPersistentStorages, am auth.AccountMapper) *InMemoryStorage { return &InMemoryStorage{ - cis: cis, - ils: ils, - ols: ols, - am: am, + persistentStorage: persistentStorage, + am: am, } } @@ -39,18 +33,19 @@ func NewInMemoryStorage( // Heavy operation func (s *InMemoryStorage) Load(ctx sdk.Context) { - inLinks, outLinks, err := s.ils.GetAllLinks(ctx) + inLinks, outLinks, err := s.persistentStorage.InLinks.GetAllLinks(ctx) if err != nil { cmn.Exit(err.Error()) } - cidsIndexes := s.cis.GetFullCidsIndex(ctx) + cidsIndexes := s.persistentStorage.CidIndex.GetFullCidsIndex(ctx) s.inLinks = inLinks s.outLinks = outLinks s.cidsIndexes = cidsIndexes s.cidsCount = uint64(len(cidsIndexes)) s.userStake = GetAllAccountsStakes(ctx, s.am) + s.cidRank = s.persistentStorage.Rank.GetFullRank(ctx) } // Also returns bool flag, whether index exists diff --git a/cosmos/poc/app/storage/rank.go b/cosmos/poc/app/storage/rank.go new file mode 100644 index 00000000..b4bbc1e8 --- /dev/null +++ b/cosmos/poc/app/storage/rank.go @@ -0,0 +1,52 @@ +package storage + +import ( + b "encoding/binary" + sdk "github.com/cosmos/cosmos-sdk/types" + "math" +) + +type RankStorage struct { + cis CidIndexStorage + key *sdk.KVStoreKey +} + +func NewRankStorage(cis CidIndexStorage, key *sdk.KVStoreKey) RankStorage { + return RankStorage{ + cis: cis, + key: key, + } +} + +// CIDs index is array of all added CIDs, sorted asc by first link time. +// - for given link, CIDs added in order [CID1, CID2] (if they both new to chain) +// This method performs lookup of CIDs, returns index value, or create and put in index new value if not exists. +func (rs RankStorage) StoreFullRank(ctx sdk.Context, ranks []float64) { + + store := ctx.KVStore(rs.key) + + var indexAsBytes [8]byte + var rankAsBytes [8]byte + for i, rank := range ranks { + b.LittleEndian.PutUint64(indexAsBytes[:], uint64(i)) + b.LittleEndian.PutUint64(rankAsBytes[:], math.Float64bits(rank)) + store.Set(indexAsBytes[:], rankAsBytes[:]) + } +} + +// returns all added cids +func (rs RankStorage) GetFullRank(ctx sdk.Context) []float64 { + + cidsCount := rs.cis.GetCidsCount(ctx) + ranks := make([]float64, cidsCount) + + store := ctx.KVStore(rs.key) + iterator := store.Iterator(nil, nil) + + for iterator.Valid() { + ranks[b.LittleEndian.Uint64(iterator.Key())] = math.Float64frombits(b.LittleEndian.Uint64(iterator.Value())) + iterator.Next() + } + iterator.Close() + return ranks +} diff --git a/cosmos/poc/app/storage/types.go b/cosmos/poc/app/storage/types.go index 2cecf9a3..108ed457 100644 --- a/cosmos/poc/app/storage/types.go +++ b/cosmos/poc/app/storage/types.go @@ -16,3 +16,11 @@ type LinkedCids struct { ToCid CidNumber Creator AccountNumber } + +// All addition storages introduced by cyberd +type CyberdPersistentStorages struct { + CidIndex CidIndexStorage + InLinks LinksStorage //incoming links storage + OutLinks LinksStorage //outgoing links storage + Rank RankStorage +}