Crates.io | pallet-encointer-bazaar |
lib.rs | pallet-encointer-bazaar |
version | 14.1.0 |
source | src |
created_at | 2023-10-27 07:13:28.474849 |
updated_at | 2024-10-21 13:13:33.226229 |
description | Bazaar pallet for the Encointer blockchain runtime |
homepage | https://encointer.org |
repository | https://github.com/encointer/pallets |
max_upload_size | |
id | 1015655 |
size | 72,362 |
This crate is part of Encointer blockchain logic, built on substrate / polkadot-sdk
For high-level technical as well as use case documentation, please refer to our book
this is a design document WIP and does not reflect the current implementation at all times
The encointer bazaar shall
For good API performance and dev experience, encointer nodes shall offer handy queries for bazaar. Usually, queries only concern one community
bazaar_getMyLocalBusinesses(who: AccountId)
returns: JsonArray<local_business: AccountId>
get all businesses controlled by who. Needs to iterate through all proxy accounts to see which ones delegate to who
bazaar_getLocalBusinesses(cid: CommunityIdentifier)
returns: JsonArray<(local_business: AccountId, json: url)>
get all business accounts for a specific community with their metadata url
bazaar_getOfferings(cid: CommunityIdentifier, local_business?: AccountId, since?: BlockNumber)
returns: JsonArray<(offering: url)>
optional:
local_business: only query offerings for that business
since: allows to filter by updated block height to query fresh entries only
BusinessRegistry: double_map(CommunityId, BusinessAccountId) -> (business_url, last_oid)
OfferingRegistry: double_map((CommunityId, BusinessAccountId), OfferingId) -> (offering_url)
BusinessAccountId is the public key of an anonymous proxy aka the business. The described tuples/triples are wrapped in value type objects.
createBusiness(CommunityId, business_url) {
var BusinessAccountId = new AnonymousProxy(sender);
BusinessRegistry.insert(CommunityId,
BusinessAccountId,
(business_url, 1, currrent_block_number));
}
updateBusiness(CommunityId, BusinessAccountId, new_business_url) {
verify(BusinessAccountId, sender);
BusinessRegistry.mutate(CommunityId, BusinessAccountId, (new_business_url, counter, current_block_number));
}
deleteBusiness(CommunityId, BusinessAccountId) {
verify(BusinessAccountId, sender);
BusinessRegistry.remove(CommunityId, BusinessAccountId);
OfferingRegistry.remove_prefix((CommunityId, BusinessId));
}
createOffering(CommunityId, BusinessAccountId, offering_url) {
verify(BusinessAccountId, sender);
var OfferingId = BusinessRegistry.get(CommunityId, BusinessAccountId).counter++
OfferingRegistry.insert((CommunityId, BusinessAccountId), OfferingId, (offering_url, block_number));
return OfferingId;
}
updateOffering(BusinessAccountId, OfferingId, new_offering_url) {
verify(BusinessAccountId, sender);
OfferingRegistry.mutate((CommunityId, BusinessAccountId), OfferingId, (BusinessAccountId, new_offering_url));
}
deleteOffering(BusinessAccountId, OfferingId) {
verify(BusinessAccountId, sender);
OfferingRegistry.remove((CommunityId, BusinessAccountId), OfferingId);
}
viewBusinesses(cid) {
return BusinessRegistry.get(cid);
}
viewOfferings(cid) {
return BusinessRegistry.get(cid).flatMap(bid -> OfferingRegistry.get(bid));
}
viewOfferings(bid) {
return OfferingRegistry.get(bid);
}
The proposed implementation of viewOfferings for a certain business has O(n) complexity. It should only be evaluated through a off-chain rpc.
complexity Vec
vs map
for sets:
operation | vec |
map |
---|---|---|
membership check | DB Reads: O(1) Decoding: O(n) Search: O(log n) | DB Reads: O(1) |
update | DB Writes: O(1) Encoding: O(n) | DB Reads: O(1) Encoding: O(1) DB Writes: O(1) |
iterate | DB Reads: O(1) Decoding: O(n) Processing: O(n) | DB Reads: O(n) Decoding: O(n) Processing: O(n) |
iteration complexity (where vec would be better) is irrelevant because the bazaar pallet doesn't iterate
obviously, map
scales better in terms of dispatchable weight
for large n
with no disadvantage for large number of calls with small n
. Moreover, weight
is constant, irrespective of n
the mobile app or web interface will usually fetch the entire set for a given cid
, therefore Vec
would be lighter to use. However, if we add a custom rpc api to fetch these sets, we can offer a convenient API while only putting a little more load on the API node