Skip to content
This repository has been archived by the owner on Oct 11, 2024. It is now read-only.

Commit

Permalink
Optimize GetOrderStatuses by using getBulk
Browse files Browse the repository at this point in the history
  • Loading branch information
albrow committed Jul 27, 2020
1 parent 0b29667 commit abff91e
Show file tree
Hide file tree
Showing 2 changed files with 66 additions and 63 deletions.
59 changes: 30 additions & 29 deletions packages/mesh-browser-lite/src/database.ts
Original file line number Diff line number Diff line change
Expand Up @@ -180,7 +180,7 @@ export class Database {
const alreadyStored: string[] = [];
const addedMap = new Map<string, Order>();
const removed: Order[] = [];
await this._db.transaction('rw', this._orders, async () => {
await this._db.transaction('rw!', this._orders, async () => {
for (const order of orders) {
try {
await this._orders.add(order);
Expand Down Expand Up @@ -222,7 +222,7 @@ export class Database {

// GetOrder(hash common.Hash) (*types.OrderWithMetadata, error)
public async getOrderAsync(hash: string): Promise<Order> {
return this._db.transaction('rw!', this._orders, async () => {
return this._db.transaction('r!', this._orders, async () => {
const order = await this._orders.get(hash);
if (order === undefined) {
throw newNotFoundError();
Expand All @@ -233,43 +233,44 @@ export class Database {

// GetOrderStatuses(hashes []common.Hash) (statuses []StoredOrderStatus, err error)
public async getOrderStatusesAsync(hashes: string[]): Promise<StoredOrderStatus[]> {
let orders: Order[] = [];
await this._db.transaction('r!', this._orders, async () => {
orders = await this._orders.bulkGet(hashes);
});
const statuses: StoredOrderStatus[] = [];
await this._db.transaction('rw!', this._orders, async () => {
for (const hash of hashes) {
const order = await this._orders.get(hash);
if (order === undefined) {
statuses.push({
isStored: false,
isMarkedRemoved: false,
});
} else if (order.isRemoved) {
statuses.push({
isStored: true,
isMarkedRemoved: true,
fillableTakerAssetAmount: order.fillableTakerAssetAmount,
});
} else {
statuses.push({
isStored: true,
isMarkedRemoved: false,
fillableTakerAssetAmount: order.fillableTakerAssetAmount,
});
}
for (const order of orders) {
if (order === undefined) {
statuses.push({
isStored: false,
isMarkedRemoved: false,
});
} else if (order.isRemoved) {
statuses.push({
isStored: true,
isMarkedRemoved: true,
fillableTakerAssetAmount: order.fillableTakerAssetAmount,
});
} else {
statuses.push({
isStored: true,
isMarkedRemoved: false,
fillableTakerAssetAmount: order.fillableTakerAssetAmount,
});
}
});
}
return statuses;
}

// FindOrders(opts *OrderQuery) ([]*types.OrderWithMetadata, error)
public async findOrdersAsync(query?: OrderQuery): Promise<Order[]> {
return this._db.transaction('rw!', this._orders, async () => {
return this._db.transaction('r!', this._orders, async () => {
return findRecordsAsync(this._orders, query);
});
}

// CountOrders(opts *OrderQuery) (int, error)
public async countOrdersAsync(query?: OrderQuery): Promise<number> {
return this._db.transaction('rw!', this._orders, async () => {
return this._db.transaction('r!', this._orders, async () => {
if (!canUseNativeDexieIndexes(this._orders, query)) {
// As a fallback, implement the query inefficiently (in-memory).
// Note(albrow): If needed we can optimize specific common queries with compound indexes.
Expand Down Expand Up @@ -379,7 +380,7 @@ export class Database {

// GetMiniHeader(hash common.Hash) (*types.MiniHeader, error)
public async getMiniHeaderAsync(hash: string): Promise<MiniHeader> {
return this._db.transaction('rw!', this._miniHeaders, async () => {
return this._db.transaction('r!', this._miniHeaders, async () => {
const miniHeader = await this._miniHeaders.get(hash);
if (miniHeader === undefined) {
throw newNotFoundError();
Expand All @@ -390,7 +391,7 @@ export class Database {

// FindMiniHeaders(opts *MiniHeaderQuery) ([]*types.MiniHeader, error)
public async findMiniHeadersAsync(query: MiniHeaderQuery): Promise<MiniHeader[]> {
return this._db.transaction('rw!', this._miniHeaders, async () => {
return this._db.transaction('r!', this._miniHeaders, async () => {
return findRecordsAsync(this._miniHeaders, query);
});
}
Expand All @@ -417,7 +418,7 @@ export class Database {

// GetMetadata() (*types.Metadata, error)
public async getMetadataAsync(): Promise<Metadata> {
return this._db.transaction('rw!', this._metadata, async () => {
return this._db.transaction('r!', this._metadata, async () => {
return this._getMetadataAsync();
});
}
Expand Down
70 changes: 36 additions & 34 deletions packages/mesh-webpack-example/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import { BigNumber, Mesh, OrderEvent, SignedOrder, SupportedProvider } from '@0x
(async () => {
// Configure Mesh to use web3.currentProvider (e.g. provided by MetaMask).
const mesh = new Mesh({
verbosity: 4,
verbosity: 2,
ethereumChainID: 1,
web3Provider: (window as any).web3.currentProvider as SupportedProvider,
});
Expand All @@ -14,44 +14,46 @@ import { BigNumber, Mesh, OrderEvent, SignedOrder, SupportedProvider } from '@0x
console.error(err);
});

// This handler will be called whenever an order is added, expired,
// cancelled, or filled.
mesh.onOrderEvents((events: OrderEvent[]) => {
for (const event of events) {
console.log(event);
}
});
// // This handler will be called whenever an order is added, expired,
// // cancelled, or filled.
// mesh.onOrderEvents((events: OrderEvent[]) => {
// for (const event of events) {
// console.log(event);
// }
// });

(window as any).mesh = mesh;

// Start Mesh *after* we set up the handlers.
await mesh.startAsync();

// This order is for demonstration purposes only and will likely be expired
// by the time you run this example. If so, it will be rejected by Mesh. You
// can replace it with a valid order.
const order: SignedOrder = {
signature:
'0x1c68eb1e2577e9f51776bdb06ec51fcec9aec0ea1565eca5e243917cecaafaa46b3b9590ff6575bf1c048d0b4ec5773a2e3a8df3bf117e1613e2a7b57d6f95c95a02',
senderAddress: '0x0000000000000000000000000000000000000000',
makerAddress: '0x4418755f710468e223797a006603e29937e825bc',
takerAddress: '0x0000000000000000000000000000000000000000',
makerFee: new BigNumber('0'),
takerFee: new BigNumber('0'),
makerAssetAmount: new BigNumber('3000000000'),
takerAssetAmount: new BigNumber('19500000000000000000'),
makerAssetData: '0xf47261b0000000000000000000000000a0b86991c6218b36c1d19d4a2e9eb0ce3606eb48',
takerAssetData: '0xf47261b0000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2',
salt: new BigNumber('1579725034907'),
exchangeAddress: '0x61935cbdd02287b511119ddb11aeb42f1593b7ef',
feeRecipientAddress: '0xa258b39954cef5cb142fd567a46cddb31a670124',
expirationTimeSeconds: new BigNumber('1580329834'),
makerFeeAssetData: '0x',
chainId: 1,
takerFeeAssetData: '0x',
};
// // This order is for demonstration purposes only and will likely be expired
// // by the time you run this example. If so, it will be rejected by Mesh. You
// // can replace it with a valid order.
// const order: SignedOrder = {
// signature:
// '0x1c68eb1e2577e9f51776bdb06ec51fcec9aec0ea1565eca5e243917cecaafaa46b3b9590ff6575bf1c048d0b4ec5773a2e3a8df3bf117e1613e2a7b57d6f95c95a02',
// senderAddress: '0x0000000000000000000000000000000000000000',
// makerAddress: '0x4418755f710468e223797a006603e29937e825bc',
// takerAddress: '0x0000000000000000000000000000000000000000',
// makerFee: new BigNumber('0'),
// takerFee: new BigNumber('0'),
// makerAssetAmount: new BigNumber('3000000000'),
// takerAssetAmount: new BigNumber('19500000000000000000'),
// makerAssetData: '0xf47261b0000000000000000000000000a0b86991c6218b36c1d19d4a2e9eb0ce3606eb48',
// takerAssetData: '0xf47261b0000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2',
// salt: new BigNumber('1579725034907'),
// exchangeAddress: '0x61935cbdd02287b511119ddb11aeb42f1593b7ef',
// feeRecipientAddress: '0xa258b39954cef5cb142fd567a46cddb31a670124',
// expirationTimeSeconds: new BigNumber('1580329834'),
// makerFeeAssetData: '0x',
// chainId: 1,
// takerFeeAssetData: '0x',
// };

// Add the order and log the result.
const result = await mesh.addOrdersAsync([order]);
console.log(result);
// // Add the order and log the result.
// const result = await mesh.addOrdersAsync([order]);
// console.log(result);
})().catch(err => {
console.error(err);
});
Expand Down

0 comments on commit abff91e

Please sign in to comment.