@o1-labs/mina-archive-node-graphql 0.0.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +321 -0
- package/build/benchmark/setup.js +32 -0
- package/build/benchmark/setup.js.map +1 -0
- package/build/src/blockchain/constants.js +2 -0
- package/build/src/blockchain/constants.js.map +1 -0
- package/build/src/blockchain/types.js +7 -0
- package/build/src/blockchain/types.js.map +1 -0
- package/build/src/blockchain/utils.js +39 -0
- package/build/src/blockchain/utils.js.map +1 -0
- package/build/src/consensus/mina-consensus.js +59 -0
- package/build/src/consensus/mina-consensus.js.map +1 -0
- package/build/src/context.js +10 -0
- package/build/src/context.js.map +1 -0
- package/build/src/db/archive-node-adapter/archive-node-adapter.interface.js +2 -0
- package/build/src/db/archive-node-adapter/archive-node-adapter.interface.js.map +1 -0
- package/build/src/db/archive-node-adapter/archive-node-adapter.js +47 -0
- package/build/src/db/archive-node-adapter/archive-node-adapter.js.map +1 -0
- package/build/src/db/sql/events-actions/queries.js +438 -0
- package/build/src/db/sql/events-actions/queries.js.map +1 -0
- package/build/src/db/sql/events-actions/types.js +2 -0
- package/build/src/db/sql/events-actions/types.js.map +1 -0
- package/build/src/errors/error.js +17 -0
- package/build/src/errors/error.js.map +1 -0
- package/build/src/index.js +27 -0
- package/build/src/index.js.map +1 -0
- package/build/src/resolvers-types.js +8 -0
- package/build/src/resolvers-types.js.map +1 -0
- package/build/src/resolvers.js +67 -0
- package/build/src/resolvers.js.map +1 -0
- package/build/src/server/plugins.js +39 -0
- package/build/src/server/plugins.js.map +1 -0
- package/build/src/server/server.js +25 -0
- package/build/src/server/server.js.map +1 -0
- package/build/src/services/actions-service/actions-service.interface.js +2 -0
- package/build/src/services/actions-service/actions-service.interface.js.map +1 -0
- package/build/src/services/actions-service/actions-service.js +94 -0
- package/build/src/services/actions-service/actions-service.js.map +1 -0
- package/build/src/services/blocks-service/blocks-service.interface.js +2 -0
- package/build/src/services/blocks-service/blocks-service.interface.js.map +1 -0
- package/build/src/services/blocks-service/blocks-service.js +263 -0
- package/build/src/services/blocks-service/blocks-service.js.map +1 -0
- package/build/src/services/data-adapters/database-row-adapters.js +116 -0
- package/build/src/services/data-adapters/database-row-adapters.js.map +1 -0
- package/build/src/services/events-service/events-service.interface.js +2 -0
- package/build/src/services/events-service/events-service.interface.js.map +1 -0
- package/build/src/services/events-service/events-service.js +64 -0
- package/build/src/services/events-service/events-service.js.map +1 -0
- package/build/src/services/network-service/network-service.interface.js +2 -0
- package/build/src/services/network-service/network-service.interface.js.map +1 -0
- package/build/src/services/network-service/network-service.js +31 -0
- package/build/src/services/network-service/network-service.js.map +1 -0
- package/build/src/tracing/jaeger-setup.js +39 -0
- package/build/src/tracing/jaeger-setup.js.map +1 -0
- package/build/src/tracing/jaeger-tracing.js +29 -0
- package/build/src/tracing/jaeger-tracing.js.map +1 -0
- package/build/src/tracing/tracer.js +31 -0
- package/build/src/tracing/tracer.js.map +1 -0
- package/build/tests/__mocks__/generate_mock_data.js +13 -0
- package/build/tests/__mocks__/generate_mock_data.js.map +1 -0
- package/build/tests/consensus/run-compare.js +40 -0
- package/build/tests/consensus/run-compare.js.map +1 -0
- package/build/tests/consensus/select-consensus-precomputed.js +80 -0
- package/build/tests/consensus/select-consensus-precomputed.js.map +1 -0
- package/build/tests/consensus/types.js +15 -0
- package/build/tests/consensus/types.js.map +1 -0
- package/build/tests/devnet-dump/devnet-dump.test.js +311 -0
- package/build/tests/devnet-dump/devnet-dump.test.js.map +1 -0
- package/build/tests/devnet-dump/setup.js +58 -0
- package/build/tests/devnet-dump/setup.js.map +1 -0
- package/build/tests/integration/integration.test.js +226 -0
- package/build/tests/integration/integration.test.js.map +1 -0
- package/build/tests/integration/setup.js +82 -0
- package/build/tests/integration/setup.js.map +1 -0
- package/build/tests/live-api/actions.test.js +4 -0
- package/build/tests/live-api/actions.test.js.map +1 -0
- package/build/tests/live-api/blocks.test.js +116 -0
- package/build/tests/live-api/blocks.test.js.map +1 -0
- package/build/tests/live-api/events.test.js +97 -0
- package/build/tests/live-api/events.test.js.map +1 -0
- package/build/tests/live-api/networkState.test.js +27 -0
- package/build/tests/live-api/networkState.test.js.map +1 -0
- package/build/tests/live-network/live-network.test.js +144 -0
- package/build/tests/live-network/live-network.test.js.map +1 -0
- package/build/tests/live-network/setup.js +206 -0
- package/build/tests/live-network/setup.js.map +1 -0
- package/build/tests/resolvers.test.js +475 -0
- package/build/tests/resolvers.test.js.map +1 -0
- package/build/tests/services/actions-service/actions-service.test.js +124 -0
- package/build/tests/services/actions-service/actions-service.test.js.map +1 -0
- package/build/tests/services/blocks-service/blocks-service.test.js +348 -0
- package/build/tests/services/blocks-service/blocks-service.test.js.map +1 -0
- package/build/tests/services/events-service/events-service.test.js +185 -0
- package/build/tests/services/events-service/events-service.test.js.map +1 -0
- package/build/tests/test-helpers.js +11 -0
- package/build/tests/test-helpers.js.map +1 -0
- package/build/tests/unit/blockchain-utils.test.js +106 -0
- package/build/tests/unit/blockchain-utils.test.js.map +1 -0
- package/build/tests/unit/consensus.test.js +154 -0
- package/build/tests/unit/consensus.test.js.map +1 -0
- package/build/tests/unit/error-handling.test.js +52 -0
- package/build/tests/unit/error-handling.test.js.map +1 -0
- package/build/tests/utils.test.js +313 -0
- package/build/tests/utils.test.js.map +1 -0
- package/build/zkapp/contract.js +144 -0
- package/build/zkapp/contract.js.map +1 -0
- package/build/zkapp/utils.js +174 -0
- package/build/zkapp/utils.js.map +1 -0
- package/package.json +85 -0
- package/schema.graphql +221 -0
- package/src/blockchain/constants.ts +2 -0
- package/src/blockchain/types.ts +121 -0
- package/src/blockchain/utils.ts +54 -0
- package/src/consensus/mina-consensus.ts +137 -0
- package/src/context.ts +18 -0
- package/src/db/archive-node-adapter/archive-node-adapter.interface.ts +23 -0
- package/src/db/archive-node-adapter/archive-node-adapter.ts +101 -0
- package/src/db/sql/events-actions/queries.ts +490 -0
- package/src/db/sql/events-actions/types.ts +208 -0
- package/src/envionment.d.ts +18 -0
- package/src/errors/error.ts +20 -0
- package/src/index.ts +31 -0
- package/src/resolvers-types.ts +754 -0
- package/src/resolvers.ts +102 -0
- package/src/server/plugins.ts +56 -0
- package/src/server/server.ts +30 -0
- package/src/services/actions-service/actions-service.interface.ts +9 -0
- package/src/services/actions-service/actions-service.ts +195 -0
- package/src/services/blocks-service/blocks-service.interface.ts +11 -0
- package/src/services/blocks-service/blocks-service.ts +407 -0
- package/src/services/data-adapters/database-row-adapters.ts +261 -0
- package/src/services/events-service/events-service.interface.ts +6 -0
- package/src/services/events-service/events-service.ts +118 -0
- package/src/services/network-service/network-service.interface.ts +5 -0
- package/src/services/network-service/network-service.ts +53 -0
- package/src/tracing/jaeger-setup.ts +65 -0
- package/src/tracing/jaeger-tracing.ts +44 -0
- package/src/tracing/tracer.ts +52 -0
- package/tsconfig.json +104 -0
package/src/resolvers.ts
ADDED
|
@@ -0,0 +1,102 @@
|
|
|
1
|
+
import { makeExecutableSchema } from '@graphql-tools/schema';
|
|
2
|
+
import { Resolvers } from './resolvers-types.js';
|
|
3
|
+
import { visit, print, parse } from 'graphql';
|
|
4
|
+
import fs from 'fs';
|
|
5
|
+
import path from 'path';
|
|
6
|
+
import { fileURLToPath } from 'url';
|
|
7
|
+
import {
|
|
8
|
+
TracingState,
|
|
9
|
+
setSpanNameFromGraphQLContext,
|
|
10
|
+
} from './tracing/tracer.js';
|
|
11
|
+
|
|
12
|
+
const __filename = fileURLToPath(import.meta.url);
|
|
13
|
+
const __dirname = path.dirname(__filename);
|
|
14
|
+
const schemaPath = path.resolve(__dirname, '../../schema.graphql');
|
|
15
|
+
|
|
16
|
+
const fullResolvers: Resolvers = {
|
|
17
|
+
Query: {
|
|
18
|
+
events: async (_, { input }, context) => {
|
|
19
|
+
const graphQLSpan = setSpanNameFromGraphQLContext(
|
|
20
|
+
context,
|
|
21
|
+
'events.graphql'
|
|
22
|
+
);
|
|
23
|
+
return context.db_client.getEvents(input, {
|
|
24
|
+
tracingState: new TracingState(graphQLSpan),
|
|
25
|
+
});
|
|
26
|
+
},
|
|
27
|
+
actions: async (_, { input }, context) => {
|
|
28
|
+
const graphQLSpan = setSpanNameFromGraphQLContext(
|
|
29
|
+
context,
|
|
30
|
+
'actions.graphql'
|
|
31
|
+
);
|
|
32
|
+
return context.db_client.getActions(input, {
|
|
33
|
+
tracingState: new TracingState(graphQLSpan),
|
|
34
|
+
});
|
|
35
|
+
},
|
|
36
|
+
networkState: async (_, __, context) => {
|
|
37
|
+
const graphQLSpan = setSpanNameFromGraphQLContext(
|
|
38
|
+
context,
|
|
39
|
+
'networkState.graphql'
|
|
40
|
+
);
|
|
41
|
+
return context.db_client.getNetworkState({
|
|
42
|
+
tracingState: new TracingState(graphQLSpan),
|
|
43
|
+
});
|
|
44
|
+
},
|
|
45
|
+
blocks: async (_, { query, limit, sortBy }, context) => {
|
|
46
|
+
const graphQLSpan = setSpanNameFromGraphQLContext(
|
|
47
|
+
context,
|
|
48
|
+
'blocks.graphql'
|
|
49
|
+
);
|
|
50
|
+
return context.db_client.getBlocks(query, limit, sortBy, {
|
|
51
|
+
tracingState: new TracingState(graphQLSpan),
|
|
52
|
+
});
|
|
53
|
+
},
|
|
54
|
+
},
|
|
55
|
+
};
|
|
56
|
+
|
|
57
|
+
let resolvers: Resolvers = fullResolvers;
|
|
58
|
+
let typeDefs: string | undefined = undefined;
|
|
59
|
+
|
|
60
|
+
// If the ENABLED_QUERIES environment variable is set, filter the schema and resolvers.
|
|
61
|
+
if (process.env.ENABLED_QUERIES !== undefined) {
|
|
62
|
+
const enabledQueries = process.env.ENABLED_QUERIES.split(',').map((q) =>
|
|
63
|
+
q.trim()
|
|
64
|
+
);
|
|
65
|
+
|
|
66
|
+
// If the list is not empty, filter the resolvers.
|
|
67
|
+
if (enabledQueries.length > 0) {
|
|
68
|
+
resolvers = {
|
|
69
|
+
Query: Object.fromEntries(
|
|
70
|
+
Object.entries(fullResolvers.Query || {}).filter(([queryName]) =>
|
|
71
|
+
enabledQueries.includes(queryName)
|
|
72
|
+
)
|
|
73
|
+
),
|
|
74
|
+
};
|
|
75
|
+
|
|
76
|
+
// Filter the schema AST.
|
|
77
|
+
const typeDefsString = fs.readFileSync(schemaPath, 'utf-8');
|
|
78
|
+
const typeDefsAst = parse(typeDefsString);
|
|
79
|
+
const modifiedAst = visit(typeDefsAst, {
|
|
80
|
+
ObjectTypeDefinition(node) {
|
|
81
|
+
if (node.name.value === 'Query') {
|
|
82
|
+
return {
|
|
83
|
+
...node,
|
|
84
|
+
fields: node.fields?.filter((field) =>
|
|
85
|
+
enabledQueries.includes(field.name.value)
|
|
86
|
+
),
|
|
87
|
+
};
|
|
88
|
+
}
|
|
89
|
+
return node;
|
|
90
|
+
},
|
|
91
|
+
});
|
|
92
|
+
typeDefs = print(modifiedAst);
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
// Create the executable schema.
|
|
97
|
+
const schema = makeExecutableSchema({
|
|
98
|
+
resolvers: [resolvers],
|
|
99
|
+
typeDefs: typeDefs || fs.readFileSync(schemaPath, 'utf-8'),
|
|
100
|
+
});
|
|
101
|
+
|
|
102
|
+
export { resolvers, schema };
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
import { useLogger } from '@envelop/core';
|
|
2
|
+
import { useGraphQlJit } from '@envelop/graphql-jit';
|
|
3
|
+
import { useDisableIntrospection } from '@envelop/disable-introspection';
|
|
4
|
+
import { useOpenTelemetry } from '@envelop/opentelemetry';
|
|
5
|
+
import { inspect } from 'node:util';
|
|
6
|
+
|
|
7
|
+
import { initJaegerProvider } from '../tracing/jaeger-tracing.js';
|
|
8
|
+
|
|
9
|
+
export { buildPlugins };
|
|
10
|
+
|
|
11
|
+
async function buildPlugins() {
|
|
12
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
13
|
+
const plugins: any[] = [];
|
|
14
|
+
plugins.push(useGraphQlJit());
|
|
15
|
+
|
|
16
|
+
if (process.env.ENABLE_LOGGING) {
|
|
17
|
+
const provider = await initJaegerProvider();
|
|
18
|
+
plugins.push(
|
|
19
|
+
useOpenTelemetry(
|
|
20
|
+
{
|
|
21
|
+
resolvers: true, // Tracks resolvers calls, and tracks resolvers thrown errors
|
|
22
|
+
variables: true, // Includes the operation variables values as part of the metadata collected
|
|
23
|
+
result: true, // Includes execution result object as part of the metadata collected
|
|
24
|
+
},
|
|
25
|
+
provider
|
|
26
|
+
)
|
|
27
|
+
);
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
if (!process.env.ENABLE_INTROSPECTION) {
|
|
31
|
+
plugins.push(useDisableIntrospection());
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
plugins.push(
|
|
35
|
+
useLogger({
|
|
36
|
+
logFn: (eventName, args) => {
|
|
37
|
+
if (args?.result?.errors) {
|
|
38
|
+
console.debug(
|
|
39
|
+
eventName,
|
|
40
|
+
inspect(args.args.contextValue.params, {
|
|
41
|
+
showHidden: false,
|
|
42
|
+
depth: null,
|
|
43
|
+
colors: true,
|
|
44
|
+
}),
|
|
45
|
+
inspect(args.result.errors, {
|
|
46
|
+
showHidden: false,
|
|
47
|
+
depth: null,
|
|
48
|
+
colors: true,
|
|
49
|
+
})
|
|
50
|
+
);
|
|
51
|
+
}
|
|
52
|
+
},
|
|
53
|
+
})
|
|
54
|
+
);
|
|
55
|
+
return plugins;
|
|
56
|
+
}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { createYoga, LogLevel } from 'graphql-yoga';
|
|
2
|
+
import { createServer } from 'http';
|
|
3
|
+
import { Plugin } from '@envelop/core';
|
|
4
|
+
import { schema } from '../resolvers.js';
|
|
5
|
+
import type { GraphQLContext } from '../context.js';
|
|
6
|
+
|
|
7
|
+
export { BLOCK_RANGE_SIZE, ENABLE_BLOCK_TRANSACTION_DETAILS, buildServer };
|
|
8
|
+
|
|
9
|
+
const LOG_LEVEL = (process.env.LOG_LEVEL as LogLevel) || 'info';
|
|
10
|
+
const BLOCK_RANGE_SIZE = Number(process.env.BLOCK_RANGE_SIZE) || 10000;
|
|
11
|
+
const ENABLE_BLOCK_TRANSACTION_DETAILS =
|
|
12
|
+
process.env.ENABLE_BLOCK_TRANSACTION_DETAILS === 'true';
|
|
13
|
+
|
|
14
|
+
function buildServer(context: GraphQLContext, plugins: Plugin[]) {
|
|
15
|
+
const yoga = createYoga<GraphQLContext>({
|
|
16
|
+
schema,
|
|
17
|
+
logging: LOG_LEVEL,
|
|
18
|
+
graphqlEndpoint: '/',
|
|
19
|
+
landingPage: false,
|
|
20
|
+
healthCheckEndpoint: '/healthcheck',
|
|
21
|
+
graphiql: process.env.ENABLE_GRAPHIQL === 'true' ? true : false,
|
|
22
|
+
plugins,
|
|
23
|
+
cors: {
|
|
24
|
+
origin: process.env.CORS_ORIGIN ?? '*',
|
|
25
|
+
methods: ['GET', 'POST'],
|
|
26
|
+
},
|
|
27
|
+
context,
|
|
28
|
+
});
|
|
29
|
+
return createServer(yoga);
|
|
30
|
+
}
|
|
@@ -0,0 +1,195 @@
|
|
|
1
|
+
import type postgres from 'postgres';
|
|
2
|
+
|
|
3
|
+
import {
|
|
4
|
+
BlockStatusFilter,
|
|
5
|
+
BlocksWithTransactionsMap,
|
|
6
|
+
FieldElementIdWithValueMap,
|
|
7
|
+
Action,
|
|
8
|
+
Actions,
|
|
9
|
+
} from '../../blockchain/types.js';
|
|
10
|
+
import type { ActionFilterOptionsInput } from '../../resolvers-types.js';
|
|
11
|
+
import { DEFAULT_TOKEN_ID } from '../../blockchain/constants.js';
|
|
12
|
+
import { createBlockInfo } from '../../blockchain/utils.js';
|
|
13
|
+
import {
|
|
14
|
+
getActionsQuery,
|
|
15
|
+
checkActionState,
|
|
16
|
+
} from '../../db/sql/events-actions/queries.js';
|
|
17
|
+
import {
|
|
18
|
+
partitionBlocks,
|
|
19
|
+
getElementIdFieldValues,
|
|
20
|
+
mapActionOrEvent,
|
|
21
|
+
removeRedundantEmittedFields,
|
|
22
|
+
sortAndFilterBlocks,
|
|
23
|
+
} from '../data-adapters/database-row-adapters.js';
|
|
24
|
+
import { IActionsService } from './actions-service.interface.js';
|
|
25
|
+
import {
|
|
26
|
+
TracingState,
|
|
27
|
+
extractTraceStateFromOptions,
|
|
28
|
+
} from '../../tracing/tracer.js';
|
|
29
|
+
import {
|
|
30
|
+
throwActionStateError,
|
|
31
|
+
throwBlockRangeError,
|
|
32
|
+
} from '../../errors/error.js';
|
|
33
|
+
import { BLOCK_RANGE_SIZE } from '../../server/server.js';
|
|
34
|
+
|
|
35
|
+
export { ActionsService };
|
|
36
|
+
|
|
37
|
+
class ActionsService implements IActionsService {
|
|
38
|
+
private readonly client: postgres.Sql;
|
|
39
|
+
|
|
40
|
+
constructor(client: postgres.Sql) {
|
|
41
|
+
this.client = client;
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
async getActions(
|
|
45
|
+
input: ActionFilterOptionsInput,
|
|
46
|
+
options: unknown
|
|
47
|
+
): Promise<Actions> {
|
|
48
|
+
const tracingState = extractTraceStateFromOptions(options);
|
|
49
|
+
return (await this.getActionData(input, { tracingState })) ?? [];
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
async getActionData(
|
|
53
|
+
input: ActionFilterOptionsInput,
|
|
54
|
+
{ tracingState }: { tracingState: TracingState }
|
|
55
|
+
): Promise<Actions> {
|
|
56
|
+
const sqlSpan = tracingState.startSpan('actions.SQL');
|
|
57
|
+
const rows = await this.executeActionsQuery(input);
|
|
58
|
+
|
|
59
|
+
sqlSpan.end();
|
|
60
|
+
|
|
61
|
+
const processingSpan = tracingState.startSpan('actions.processing');
|
|
62
|
+
const elementIdFieldValues = getElementIdFieldValues(rows);
|
|
63
|
+
const blocksWithTransactions = partitionBlocks(rows);
|
|
64
|
+
const actionsData = this.blocksToActions(
|
|
65
|
+
blocksWithTransactions,
|
|
66
|
+
elementIdFieldValues
|
|
67
|
+
);
|
|
68
|
+
sortAndFilterBlocks(actionsData);
|
|
69
|
+
processingSpan.end();
|
|
70
|
+
return actionsData;
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
async executeActionsQuery(input: ActionFilterOptionsInput) {
|
|
74
|
+
const { address, to, from, endActionState, fromActionState } = input;
|
|
75
|
+
|
|
76
|
+
// Check if action states exist.
|
|
77
|
+
if (fromActionState) {
|
|
78
|
+
const fromActionStateExists = await checkActionState(
|
|
79
|
+
this.client,
|
|
80
|
+
fromActionState
|
|
81
|
+
);
|
|
82
|
+
if (!fromActionStateExists || !fromActionStateExists.length) {
|
|
83
|
+
throwActionStateError(
|
|
84
|
+
`fromActionState ${fromActionState} does not exist`
|
|
85
|
+
);
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
if (endActionState) {
|
|
89
|
+
const endActionStateExists = await checkActionState(
|
|
90
|
+
this.client,
|
|
91
|
+
endActionState
|
|
92
|
+
);
|
|
93
|
+
if (!endActionStateExists || !endActionStateExists.length) {
|
|
94
|
+
throwActionStateError(
|
|
95
|
+
`endActionState ${endActionState} does not exist`
|
|
96
|
+
);
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
let { tokenId, status } = input;
|
|
100
|
+
|
|
101
|
+
tokenId ||= DEFAULT_TOKEN_ID;
|
|
102
|
+
status ||= BlockStatusFilter.all;
|
|
103
|
+
if (to && from && to < from) {
|
|
104
|
+
throwBlockRangeError('to must be greater than from');
|
|
105
|
+
}
|
|
106
|
+
if (to && from && to - from > BLOCK_RANGE_SIZE) {
|
|
107
|
+
throwBlockRangeError(
|
|
108
|
+
`The block range is too large. The maximum range is ${BLOCK_RANGE_SIZE}`
|
|
109
|
+
);
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
return getActionsQuery(
|
|
113
|
+
this.client,
|
|
114
|
+
address,
|
|
115
|
+
tokenId,
|
|
116
|
+
status,
|
|
117
|
+
to?.toString(),
|
|
118
|
+
from?.toString(),
|
|
119
|
+
fromActionState?.toString(),
|
|
120
|
+
endActionState?.toString()
|
|
121
|
+
);
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
blocksToActions(
|
|
125
|
+
blocksWithTransactions: BlocksWithTransactionsMap,
|
|
126
|
+
elementIdFieldValues: FieldElementIdWithValueMap
|
|
127
|
+
) {
|
|
128
|
+
const actions: Actions = [];
|
|
129
|
+
const blockTransactionEntries = Array.from(
|
|
130
|
+
blocksWithTransactions.entries()
|
|
131
|
+
);
|
|
132
|
+
for (let i = 0; i < blockTransactionEntries.length; i++) {
|
|
133
|
+
const transactions = blockTransactionEntries[i][1];
|
|
134
|
+
const transaction = transactions.values().next().value![0];
|
|
135
|
+
const blockInfo = createBlockInfo(transaction);
|
|
136
|
+
const {
|
|
137
|
+
action_state_value1,
|
|
138
|
+
action_state_value2,
|
|
139
|
+
action_state_value3,
|
|
140
|
+
action_state_value4,
|
|
141
|
+
action_state_value5,
|
|
142
|
+
} = transaction;
|
|
143
|
+
|
|
144
|
+
const actionsData: Action[][] = [];
|
|
145
|
+
for (const [, transaction] of transactions) {
|
|
146
|
+
const filteredBlocks = removeRedundantEmittedFields(transaction);
|
|
147
|
+
const actionData = mapActionOrEvent(
|
|
148
|
+
'action',
|
|
149
|
+
filteredBlocks,
|
|
150
|
+
elementIdFieldValues
|
|
151
|
+
) as Action[];
|
|
152
|
+
actionsData.push(actionData);
|
|
153
|
+
}
|
|
154
|
+
actions.push({
|
|
155
|
+
blockInfo,
|
|
156
|
+
actionData: this.sortActions(actionsData.flat()),
|
|
157
|
+
actionState: {
|
|
158
|
+
/* eslint-disable */
|
|
159
|
+
actionStateOne: action_state_value1!,
|
|
160
|
+
actionStateTwo: action_state_value2!,
|
|
161
|
+
actionStateThree: action_state_value3!,
|
|
162
|
+
actionStateFour: action_state_value4!,
|
|
163
|
+
actionStateFive: action_state_value5!,
|
|
164
|
+
/* eslint-enable */
|
|
165
|
+
},
|
|
166
|
+
});
|
|
167
|
+
}
|
|
168
|
+
return actions;
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
sortActions(actions: Action[]): Action[] {
|
|
172
|
+
return actions.sort((a, b) => {
|
|
173
|
+
// Sort by sequence number
|
|
174
|
+
if (
|
|
175
|
+
a.transactionInfo.sequenceNumber !== b.transactionInfo.sequenceNumber
|
|
176
|
+
) {
|
|
177
|
+
return (
|
|
178
|
+
a.transactionInfo.sequenceNumber - b.transactionInfo.sequenceNumber
|
|
179
|
+
);
|
|
180
|
+
}
|
|
181
|
+
|
|
182
|
+
// Sort by account update index within the transaction
|
|
183
|
+
const aAccountUpdateIndex =
|
|
184
|
+
a.transactionInfo.zkappAccountUpdateIds.indexOf(
|
|
185
|
+
Number(a.accountUpdateId)
|
|
186
|
+
);
|
|
187
|
+
const bAccountUpdateIndex =
|
|
188
|
+
b.transactionInfo.zkappAccountUpdateIds.indexOf(
|
|
189
|
+
Number(b.accountUpdateId)
|
|
190
|
+
);
|
|
191
|
+
|
|
192
|
+
return aAccountUpdateIndex - bAccountUpdateIndex;
|
|
193
|
+
});
|
|
194
|
+
}
|
|
195
|
+
}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { Blocks } from '../../blockchain/types.js';
|
|
2
|
+
import { BlockQueryInput, BlockSortByInput } from '../../resolvers-types.js';
|
|
3
|
+
|
|
4
|
+
export interface IBlocksService {
|
|
5
|
+
getBlocks(
|
|
6
|
+
query: BlockQueryInput | null | undefined,
|
|
7
|
+
limit: number | null | undefined,
|
|
8
|
+
sortBy: BlockSortByInput | null | undefined,
|
|
9
|
+
options: unknown
|
|
10
|
+
): Promise<Blocks>;
|
|
11
|
+
}
|