@envelop/core 2.4.0-alpha-db79afa.0 → 2.4.0-alpha-05dbec7.0
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/cjs/create.js +28 -0
- package/cjs/enable-if.js +24 -0
- package/cjs/index.js +16 -0
- package/cjs/orchestrator.js +451 -0
- package/cjs/package.json +1 -0
- package/cjs/plugins/use-envelop.js +13 -0
- package/cjs/plugins/use-error-handler.js +21 -0
- package/cjs/plugins/use-extend-context.js +9 -0
- package/cjs/plugins/use-immediate-introspection.js +50 -0
- package/cjs/plugins/use-logger.js +45 -0
- package/cjs/plugins/use-masked-errors.js +90 -0
- package/cjs/plugins/use-payload-formatter.js +21 -0
- package/cjs/plugins/use-schema.js +29 -0
- package/cjs/plugins/use-timing.js +138 -0
- package/cjs/traced-orchestrator.js +134 -0
- package/cjs/traced-schema.js +68 -0
- package/cjs/utils.js +221 -0
- package/esm/create.js +24 -0
- package/esm/enable-if.js +19 -0
- package/esm/index.js +13 -0
- package/esm/orchestrator.js +447 -0
- package/esm/plugins/use-envelop.js +9 -0
- package/esm/plugins/use-error-handler.js +17 -0
- package/esm/plugins/use-extend-context.js +5 -0
- package/esm/plugins/use-immediate-introspection.js +46 -0
- package/esm/plugins/use-logger.js +41 -0
- package/esm/plugins/use-masked-errors.js +84 -0
- package/esm/plugins/use-payload-formatter.js +17 -0
- package/esm/plugins/use-schema.js +23 -0
- package/esm/plugins/use-timing.js +134 -0
- package/esm/traced-orchestrator.js +130 -0
- package/esm/traced-schema.js +64 -0
- package/esm/utils.js +207 -0
- package/package.json +33 -12
- package/{create.d.ts → typings/create.d.ts} +1 -1
- package/{enable-if.d.ts → typings/enable-if.d.ts} +0 -0
- package/typings/index.d.ts +13 -0
- package/{orchestrator.d.ts → typings/orchestrator.d.ts} +0 -0
- package/{plugins → typings/plugins}/use-envelop.d.ts +0 -0
- package/{plugins → typings/plugins}/use-error-handler.d.ts +0 -0
- package/{plugins → typings/plugins}/use-extend-context.d.ts +0 -0
- package/{plugins → typings/plugins}/use-immediate-introspection.d.ts +0 -0
- package/{plugins → typings/plugins}/use-logger.d.ts +1 -1
- package/{plugins → typings/plugins}/use-masked-errors.d.ts +3 -3
- package/{plugins → typings/plugins}/use-payload-formatter.d.ts +0 -0
- package/{plugins → typings/plugins}/use-schema.d.ts +0 -0
- package/{plugins → typings/plugins}/use-timing.d.ts +2 -2
- package/{traced-orchestrator.d.ts → typings/traced-orchestrator.d.ts} +1 -1
- package/{traced-schema.d.ts → typings/traced-schema.d.ts} +0 -0
- package/{utils.d.ts → typings/utils.d.ts} +0 -13
- package/README.md +0 -15
- package/index.d.ts +0 -13
- package/index.js +0 -1359
- package/index.mjs +0 -1317
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
export const useSchema = (schema) => {
|
|
2
|
+
return {
|
|
3
|
+
onPluginInit({ setSchema }) {
|
|
4
|
+
setSchema(schema);
|
|
5
|
+
},
|
|
6
|
+
};
|
|
7
|
+
};
|
|
8
|
+
export const useLazyLoadedSchema = (schemaLoader) => {
|
|
9
|
+
return {
|
|
10
|
+
onEnveloped({ setSchema, context }) {
|
|
11
|
+
setSchema(schemaLoader(context));
|
|
12
|
+
},
|
|
13
|
+
};
|
|
14
|
+
};
|
|
15
|
+
export const useAsyncSchema = (schemaPromise) => {
|
|
16
|
+
return {
|
|
17
|
+
onPluginInit({ setSchema }) {
|
|
18
|
+
schemaPromise.then(schemaObj => {
|
|
19
|
+
setSchema(schemaObj);
|
|
20
|
+
});
|
|
21
|
+
},
|
|
22
|
+
};
|
|
23
|
+
};
|
|
@@ -0,0 +1,134 @@
|
|
|
1
|
+
import { getOperationAST } from 'graphql';
|
|
2
|
+
import { isIntrospectionOperationString, envelopIsIntrospectionSymbol } from '../utils.js';
|
|
3
|
+
const HR_TO_NS = 1e9;
|
|
4
|
+
const NS_TO_MS = 1e6;
|
|
5
|
+
const DEFAULT_OPTIONS = {
|
|
6
|
+
onExecutionMeasurement: (args, timing) => console.log(`Operation execution "${args.operationName}" done in ${timing.ms}ms`),
|
|
7
|
+
onSubscriptionMeasurement: (args, timing) => console.log(`Operation subscription "${args.operationName}" done in ${timing.ms}ms`),
|
|
8
|
+
onParsingMeasurement: (source, timing) => console.log(`Parsing "${source}" done in ${timing.ms}ms`),
|
|
9
|
+
onValidationMeasurement: (document, timing) => { var _a, _b; return console.log(`Validation "${((_b = (_a = getOperationAST(document)) === null || _a === void 0 ? void 0 : _a.name) === null || _b === void 0 ? void 0 : _b.value) || '-'}" done in ${timing.ms}ms`); },
|
|
10
|
+
onResolverMeasurement: (info, timing) => console.log(`\tResolver of "${info.parentType.toString()}.${info.fieldName}" done in ${timing.ms}ms`),
|
|
11
|
+
onContextBuildingMeasurement: (timing) => console.log(`Context building done in ${timing.ms}ms`),
|
|
12
|
+
};
|
|
13
|
+
const deltaFrom = (hrtime) => {
|
|
14
|
+
const delta = process.hrtime(hrtime);
|
|
15
|
+
const ns = delta[0] * HR_TO_NS + delta[1];
|
|
16
|
+
return {
|
|
17
|
+
ns,
|
|
18
|
+
get ms() {
|
|
19
|
+
return ns / NS_TO_MS;
|
|
20
|
+
},
|
|
21
|
+
};
|
|
22
|
+
};
|
|
23
|
+
export const useTiming = (rawOptions) => {
|
|
24
|
+
const options = {
|
|
25
|
+
...DEFAULT_OPTIONS,
|
|
26
|
+
...(rawOptions || {}),
|
|
27
|
+
};
|
|
28
|
+
const result = {};
|
|
29
|
+
if (options.onContextBuildingMeasurement) {
|
|
30
|
+
result.onContextBuilding = ({ context }) => {
|
|
31
|
+
if (context[envelopIsIntrospectionSymbol]) {
|
|
32
|
+
return;
|
|
33
|
+
}
|
|
34
|
+
const contextStartTime = process.hrtime();
|
|
35
|
+
return () => {
|
|
36
|
+
options.onContextBuildingMeasurement(deltaFrom(contextStartTime));
|
|
37
|
+
};
|
|
38
|
+
};
|
|
39
|
+
}
|
|
40
|
+
if (options.onParsingMeasurement) {
|
|
41
|
+
result.onParse = ({ params, extendContext }) => {
|
|
42
|
+
if (options.skipIntrospection && isIntrospectionOperationString(params.source)) {
|
|
43
|
+
extendContext({
|
|
44
|
+
[envelopIsIntrospectionSymbol]: true,
|
|
45
|
+
});
|
|
46
|
+
return;
|
|
47
|
+
}
|
|
48
|
+
const parseStartTime = process.hrtime();
|
|
49
|
+
return () => {
|
|
50
|
+
options.onParsingMeasurement(params.source, deltaFrom(parseStartTime));
|
|
51
|
+
};
|
|
52
|
+
};
|
|
53
|
+
}
|
|
54
|
+
if (options.onValidationMeasurement) {
|
|
55
|
+
result.onValidate = ({ params, context }) => {
|
|
56
|
+
if (context[envelopIsIntrospectionSymbol]) {
|
|
57
|
+
return;
|
|
58
|
+
}
|
|
59
|
+
const validateStartTime = process.hrtime();
|
|
60
|
+
return () => {
|
|
61
|
+
options.onValidationMeasurement(params.documentAST, deltaFrom(validateStartTime));
|
|
62
|
+
};
|
|
63
|
+
};
|
|
64
|
+
}
|
|
65
|
+
if (options.onExecutionMeasurement) {
|
|
66
|
+
if (options.onResolverMeasurement) {
|
|
67
|
+
result.onExecute = ({ args }) => {
|
|
68
|
+
if (args.contextValue[envelopIsIntrospectionSymbol]) {
|
|
69
|
+
return;
|
|
70
|
+
}
|
|
71
|
+
const executeStartTime = process.hrtime();
|
|
72
|
+
return {
|
|
73
|
+
onExecuteDone: () => {
|
|
74
|
+
options.onExecutionMeasurement(args, deltaFrom(executeStartTime));
|
|
75
|
+
},
|
|
76
|
+
};
|
|
77
|
+
};
|
|
78
|
+
result.onResolverCalled = ({ info }) => {
|
|
79
|
+
const resolverStartTime = process.hrtime();
|
|
80
|
+
return () => {
|
|
81
|
+
options.onResolverMeasurement(info, deltaFrom(resolverStartTime));
|
|
82
|
+
};
|
|
83
|
+
};
|
|
84
|
+
}
|
|
85
|
+
else {
|
|
86
|
+
result.onExecute = ({ args }) => {
|
|
87
|
+
if (args.contextValue[envelopIsIntrospectionSymbol]) {
|
|
88
|
+
return;
|
|
89
|
+
}
|
|
90
|
+
const executeStartTime = process.hrtime();
|
|
91
|
+
return {
|
|
92
|
+
onExecuteDone: () => {
|
|
93
|
+
options.onExecutionMeasurement(args, deltaFrom(executeStartTime));
|
|
94
|
+
},
|
|
95
|
+
};
|
|
96
|
+
};
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
if (options.onSubscriptionMeasurement) {
|
|
100
|
+
if (options.onResolverMeasurement) {
|
|
101
|
+
result.onSubscribe = ({ args }) => {
|
|
102
|
+
if (args.contextValue[envelopIsIntrospectionSymbol]) {
|
|
103
|
+
return;
|
|
104
|
+
}
|
|
105
|
+
const subscribeStartTime = process.hrtime();
|
|
106
|
+
return {
|
|
107
|
+
onSubscribeResult: () => {
|
|
108
|
+
options.onSubscriptionMeasurement && options.onSubscriptionMeasurement(args, deltaFrom(subscribeStartTime));
|
|
109
|
+
},
|
|
110
|
+
};
|
|
111
|
+
};
|
|
112
|
+
result.onResolverCalled = ({ info }) => {
|
|
113
|
+
const resolverStartTime = process.hrtime();
|
|
114
|
+
return () => {
|
|
115
|
+
options.onResolverMeasurement && options.onResolverMeasurement(info, deltaFrom(resolverStartTime));
|
|
116
|
+
};
|
|
117
|
+
};
|
|
118
|
+
}
|
|
119
|
+
else {
|
|
120
|
+
result.onSubscribe = ({ args }) => {
|
|
121
|
+
if (args.contextValue[envelopIsIntrospectionSymbol]) {
|
|
122
|
+
return;
|
|
123
|
+
}
|
|
124
|
+
const subscribeStartTime = process.hrtime();
|
|
125
|
+
return {
|
|
126
|
+
onSubscribeResult: () => {
|
|
127
|
+
options.onSubscriptionMeasurement && options.onSubscriptionMeasurement(args, deltaFrom(subscribeStartTime));
|
|
128
|
+
},
|
|
129
|
+
};
|
|
130
|
+
};
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
return result;
|
|
134
|
+
};
|
|
@@ -0,0 +1,130 @@
|
|
|
1
|
+
var _a;
|
|
2
|
+
import { GraphQLSchema } from 'graphql';
|
|
3
|
+
import { isAsyncIterable } from './utils.js';
|
|
4
|
+
const getTimestamp = typeof globalThis !== 'undefined' && ((_a = globalThis === null || globalThis === void 0 ? void 0 : globalThis.performance) === null || _a === void 0 ? void 0 : _a.now) ? () => globalThis.performance.now() : () => Date.now();
|
|
5
|
+
const measure = () => {
|
|
6
|
+
const start = getTimestamp();
|
|
7
|
+
return () => {
|
|
8
|
+
const end = getTimestamp();
|
|
9
|
+
return end - start;
|
|
10
|
+
};
|
|
11
|
+
};
|
|
12
|
+
const tracingSymbol = Symbol('envelopTracing');
|
|
13
|
+
export function traceOrchestrator(orchestrator) {
|
|
14
|
+
const createTracer = (name, ctx) => {
|
|
15
|
+
const end = measure();
|
|
16
|
+
return () => {
|
|
17
|
+
ctx[tracingSymbol][name] = end();
|
|
18
|
+
};
|
|
19
|
+
};
|
|
20
|
+
return {
|
|
21
|
+
...orchestrator,
|
|
22
|
+
init: (ctx = {}) => {
|
|
23
|
+
ctx[tracingSymbol] = ctx[tracingSymbol] || {};
|
|
24
|
+
const done = createTracer('init', ctx || {});
|
|
25
|
+
try {
|
|
26
|
+
return orchestrator.init(ctx);
|
|
27
|
+
}
|
|
28
|
+
finally {
|
|
29
|
+
done();
|
|
30
|
+
}
|
|
31
|
+
},
|
|
32
|
+
parse: (ctx = {}) => {
|
|
33
|
+
ctx[tracingSymbol] = ctx[tracingSymbol] || {};
|
|
34
|
+
const actualFn = orchestrator.parse(ctx);
|
|
35
|
+
return (...args) => {
|
|
36
|
+
const done = createTracer('parse', ctx);
|
|
37
|
+
try {
|
|
38
|
+
return actualFn(...args);
|
|
39
|
+
}
|
|
40
|
+
finally {
|
|
41
|
+
done();
|
|
42
|
+
}
|
|
43
|
+
};
|
|
44
|
+
},
|
|
45
|
+
validate: (ctx = {}) => {
|
|
46
|
+
ctx[tracingSymbol] = ctx[tracingSymbol] || {};
|
|
47
|
+
const actualFn = orchestrator.validate(ctx);
|
|
48
|
+
return (...args) => {
|
|
49
|
+
const done = createTracer('validate', ctx);
|
|
50
|
+
try {
|
|
51
|
+
return actualFn(...args);
|
|
52
|
+
}
|
|
53
|
+
finally {
|
|
54
|
+
done();
|
|
55
|
+
}
|
|
56
|
+
};
|
|
57
|
+
},
|
|
58
|
+
execute: async (argsOrSchema, document, rootValue, contextValue, variableValues, operationName, fieldResolver, typeResolver) => {
|
|
59
|
+
const args = argsOrSchema instanceof GraphQLSchema
|
|
60
|
+
? {
|
|
61
|
+
schema: argsOrSchema,
|
|
62
|
+
document: document,
|
|
63
|
+
rootValue,
|
|
64
|
+
contextValue,
|
|
65
|
+
variableValues,
|
|
66
|
+
operationName,
|
|
67
|
+
fieldResolver,
|
|
68
|
+
typeResolver,
|
|
69
|
+
}
|
|
70
|
+
: argsOrSchema;
|
|
71
|
+
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
|
72
|
+
// @ts-ignore GraphQL.js types contextValue as unknown
|
|
73
|
+
const done = createTracer('execute', args.contextValue || {});
|
|
74
|
+
try {
|
|
75
|
+
const result = await orchestrator.execute(args);
|
|
76
|
+
done();
|
|
77
|
+
if (!isAsyncIterable(result)) {
|
|
78
|
+
result.extensions = result.extensions || {};
|
|
79
|
+
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
|
80
|
+
// @ts-ignore GraphQL.js types contextValue as unknown
|
|
81
|
+
result.extensions.envelopTracing = args.contextValue[tracingSymbol];
|
|
82
|
+
}
|
|
83
|
+
else {
|
|
84
|
+
// eslint-disable-next-line no-console
|
|
85
|
+
console.warn(`"traceOrchestrator" encountered a AsyncIterator which is not supported yet, so tracing data is not available for the operation.`);
|
|
86
|
+
}
|
|
87
|
+
return result;
|
|
88
|
+
}
|
|
89
|
+
catch (e) {
|
|
90
|
+
done();
|
|
91
|
+
throw e;
|
|
92
|
+
}
|
|
93
|
+
},
|
|
94
|
+
subscribe: async (argsOrSchema, document, rootValue, contextValue, variableValues, operationName, fieldResolver, subscribeFieldResolver) => {
|
|
95
|
+
const args = argsOrSchema instanceof GraphQLSchema
|
|
96
|
+
? {
|
|
97
|
+
schema: argsOrSchema,
|
|
98
|
+
document: document,
|
|
99
|
+
rootValue,
|
|
100
|
+
contextValue,
|
|
101
|
+
variableValues,
|
|
102
|
+
operationName,
|
|
103
|
+
fieldResolver,
|
|
104
|
+
subscribeFieldResolver,
|
|
105
|
+
}
|
|
106
|
+
: argsOrSchema;
|
|
107
|
+
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
|
108
|
+
// @ts-ignore GraphQL.js types contextValue as unknown
|
|
109
|
+
const done = createTracer('subscribe', args.contextValue || {});
|
|
110
|
+
try {
|
|
111
|
+
return await orchestrator.subscribe(args);
|
|
112
|
+
}
|
|
113
|
+
finally {
|
|
114
|
+
done();
|
|
115
|
+
}
|
|
116
|
+
},
|
|
117
|
+
contextFactory: (ctx = {}) => {
|
|
118
|
+
const actualFn = orchestrator.contextFactory(ctx);
|
|
119
|
+
return async (childCtx) => {
|
|
120
|
+
const done = createTracer('contextFactory', ctx);
|
|
121
|
+
try {
|
|
122
|
+
return await actualFn(childCtx);
|
|
123
|
+
}
|
|
124
|
+
finally {
|
|
125
|
+
done();
|
|
126
|
+
}
|
|
127
|
+
};
|
|
128
|
+
},
|
|
129
|
+
};
|
|
130
|
+
}
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
import { defaultFieldResolver, isIntrospectionType, isObjectType } from 'graphql';
|
|
2
|
+
export const trackedSchemaSymbol = Symbol('TRACKED_SCHEMA');
|
|
3
|
+
export const resolversHooksSymbol = Symbol('RESOLVERS_HOOKS');
|
|
4
|
+
export function prepareTracedSchema(schema) {
|
|
5
|
+
if (!schema || schema[trackedSchemaSymbol]) {
|
|
6
|
+
return;
|
|
7
|
+
}
|
|
8
|
+
schema[trackedSchemaSymbol] = true;
|
|
9
|
+
const entries = Object.values(schema.getTypeMap());
|
|
10
|
+
for (const type of entries) {
|
|
11
|
+
if (!isIntrospectionType(type) && isObjectType(type)) {
|
|
12
|
+
const fields = Object.values(type.getFields());
|
|
13
|
+
for (const field of fields) {
|
|
14
|
+
let resolverFn = (field.resolve || defaultFieldResolver);
|
|
15
|
+
field.resolve = async (root, args, context, info) => {
|
|
16
|
+
if (context && context[resolversHooksSymbol]) {
|
|
17
|
+
const hooks = context[resolversHooksSymbol];
|
|
18
|
+
const afterCalls = [];
|
|
19
|
+
for (const hook of hooks) {
|
|
20
|
+
const afterFn = await hook({
|
|
21
|
+
root,
|
|
22
|
+
args,
|
|
23
|
+
context,
|
|
24
|
+
info,
|
|
25
|
+
resolverFn,
|
|
26
|
+
replaceResolverFn: newFn => {
|
|
27
|
+
resolverFn = newFn;
|
|
28
|
+
},
|
|
29
|
+
});
|
|
30
|
+
afterFn && afterCalls.push(afterFn);
|
|
31
|
+
}
|
|
32
|
+
try {
|
|
33
|
+
let result = await resolverFn(root, args, context, info);
|
|
34
|
+
for (const afterFn of afterCalls) {
|
|
35
|
+
afterFn({
|
|
36
|
+
result,
|
|
37
|
+
setResult: newResult => {
|
|
38
|
+
result = newResult;
|
|
39
|
+
},
|
|
40
|
+
});
|
|
41
|
+
}
|
|
42
|
+
return result;
|
|
43
|
+
}
|
|
44
|
+
catch (e) {
|
|
45
|
+
let resultErr = e;
|
|
46
|
+
for (const afterFn of afterCalls) {
|
|
47
|
+
afterFn({
|
|
48
|
+
result: resultErr,
|
|
49
|
+
setResult: newResult => {
|
|
50
|
+
resultErr = newResult;
|
|
51
|
+
},
|
|
52
|
+
});
|
|
53
|
+
}
|
|
54
|
+
throw resultErr;
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
else {
|
|
58
|
+
return resolverFn(root, args, context, info);
|
|
59
|
+
}
|
|
60
|
+
};
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
}
|
package/esm/utils.js
ADDED
|
@@ -0,0 +1,207 @@
|
|
|
1
|
+
import { Kind, visit, BREAK, } from 'graphql';
|
|
2
|
+
export const envelopIsIntrospectionSymbol = Symbol('ENVELOP_IS_INTROSPECTION');
|
|
3
|
+
export function isOperationDefinition(def) {
|
|
4
|
+
return def.kind === Kind.OPERATION_DEFINITION;
|
|
5
|
+
}
|
|
6
|
+
export function isIntrospectionOperation(operation) {
|
|
7
|
+
if (operation.kind === 'OperationDefinition') {
|
|
8
|
+
let hasIntrospectionField = false;
|
|
9
|
+
visit(operation, {
|
|
10
|
+
Field: node => {
|
|
11
|
+
if (node.name.value === '__schema') {
|
|
12
|
+
hasIntrospectionField = true;
|
|
13
|
+
return BREAK;
|
|
14
|
+
}
|
|
15
|
+
},
|
|
16
|
+
});
|
|
17
|
+
return hasIntrospectionField;
|
|
18
|
+
}
|
|
19
|
+
return false;
|
|
20
|
+
}
|
|
21
|
+
export function isIntrospectionDocument(document) {
|
|
22
|
+
const operations = document.definitions.filter(isOperationDefinition);
|
|
23
|
+
return operations.some(op => isIntrospectionOperation(op));
|
|
24
|
+
}
|
|
25
|
+
export function isIntrospectionOperationString(operation) {
|
|
26
|
+
return (typeof operation === 'string' ? operation : operation.body).indexOf('__schema') !== -1;
|
|
27
|
+
}
|
|
28
|
+
function getSubscribeArgs(args) {
|
|
29
|
+
return args.length === 1
|
|
30
|
+
? args[0]
|
|
31
|
+
: {
|
|
32
|
+
schema: args[0],
|
|
33
|
+
document: args[1],
|
|
34
|
+
rootValue: args[2],
|
|
35
|
+
contextValue: args[3],
|
|
36
|
+
variableValues: args[4],
|
|
37
|
+
operationName: args[5],
|
|
38
|
+
fieldResolver: args[6],
|
|
39
|
+
subscribeFieldResolver: args[7],
|
|
40
|
+
};
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Utility function for making a subscribe function that handles polymorphic arguments.
|
|
44
|
+
*/
|
|
45
|
+
export const makeSubscribe = (subscribeFn) => ((...polyArgs) => subscribeFn(getSubscribeArgs(polyArgs)));
|
|
46
|
+
export function mapAsyncIterator(source, mapper) {
|
|
47
|
+
const iterator = source[Symbol.asyncIterator]();
|
|
48
|
+
async function mapResult(result) {
|
|
49
|
+
var _a;
|
|
50
|
+
if (result.done) {
|
|
51
|
+
return result;
|
|
52
|
+
}
|
|
53
|
+
try {
|
|
54
|
+
return { value: await mapper(result.value), done: false };
|
|
55
|
+
}
|
|
56
|
+
catch (error) {
|
|
57
|
+
try {
|
|
58
|
+
await ((_a = iterator.return) === null || _a === void 0 ? void 0 : _a.call(iterator));
|
|
59
|
+
}
|
|
60
|
+
catch (_error) {
|
|
61
|
+
/* ignore error */
|
|
62
|
+
}
|
|
63
|
+
throw error;
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
const stream = {
|
|
67
|
+
[Symbol.asyncIterator]() {
|
|
68
|
+
return stream;
|
|
69
|
+
},
|
|
70
|
+
async next() {
|
|
71
|
+
return await mapResult(await iterator.next());
|
|
72
|
+
},
|
|
73
|
+
async return() {
|
|
74
|
+
var _a;
|
|
75
|
+
const promise = (_a = iterator.return) === null || _a === void 0 ? void 0 : _a.call(iterator);
|
|
76
|
+
return promise ? await mapResult(await promise) : { value: undefined, done: true };
|
|
77
|
+
},
|
|
78
|
+
async throw(error) {
|
|
79
|
+
var _a;
|
|
80
|
+
const promise = (_a = iterator.throw) === null || _a === void 0 ? void 0 : _a.call(iterator);
|
|
81
|
+
if (promise) {
|
|
82
|
+
return await mapResult(await promise);
|
|
83
|
+
}
|
|
84
|
+
// if the source has no throw method we just re-throw error
|
|
85
|
+
// usually throw is not called anyways
|
|
86
|
+
throw error;
|
|
87
|
+
},
|
|
88
|
+
};
|
|
89
|
+
return stream;
|
|
90
|
+
}
|
|
91
|
+
function getExecuteArgs(args) {
|
|
92
|
+
return args.length === 1
|
|
93
|
+
? args[0]
|
|
94
|
+
: {
|
|
95
|
+
schema: args[0],
|
|
96
|
+
document: args[1],
|
|
97
|
+
rootValue: args[2],
|
|
98
|
+
contextValue: args[3],
|
|
99
|
+
variableValues: args[4],
|
|
100
|
+
operationName: args[5],
|
|
101
|
+
fieldResolver: args[6],
|
|
102
|
+
typeResolver: args[7],
|
|
103
|
+
};
|
|
104
|
+
}
|
|
105
|
+
/**
|
|
106
|
+
* Utility function for making a execute function that handles polymorphic arguments.
|
|
107
|
+
*/
|
|
108
|
+
export const makeExecute = (executeFn) => ((...polyArgs) => executeFn(getExecuteArgs(polyArgs)));
|
|
109
|
+
/**
|
|
110
|
+
* Returns true if the provided object implements the AsyncIterator protocol via
|
|
111
|
+
* implementing a `Symbol.asyncIterator` method.
|
|
112
|
+
*
|
|
113
|
+
* Source: https://github.com/graphql/graphql-js/blob/main/src/jsutils/isAsyncIterable.ts
|
|
114
|
+
*/
|
|
115
|
+
export function isAsyncIterable(maybeAsyncIterable) {
|
|
116
|
+
return (typeof maybeAsyncIterable === 'object' &&
|
|
117
|
+
maybeAsyncIterable != null &&
|
|
118
|
+
typeof maybeAsyncIterable[Symbol.asyncIterator] === 'function');
|
|
119
|
+
}
|
|
120
|
+
/**
|
|
121
|
+
* A utility function for handling `onExecuteDone` hook result, for simplifying the handling of AsyncIterable returned from `execute`.
|
|
122
|
+
*
|
|
123
|
+
* @param payload The payload send to `onExecuteDone` hook function
|
|
124
|
+
* @param fn The handler to be executed on each result
|
|
125
|
+
* @returns a subscription for streamed results, or undefined in case of an non-async
|
|
126
|
+
*/
|
|
127
|
+
export function handleStreamOrSingleExecutionResult(payload, fn) {
|
|
128
|
+
if (isAsyncIterable(payload.result)) {
|
|
129
|
+
return { onNext: fn };
|
|
130
|
+
}
|
|
131
|
+
fn({
|
|
132
|
+
args: payload.args,
|
|
133
|
+
result: payload.result,
|
|
134
|
+
setResult: payload.setResult,
|
|
135
|
+
});
|
|
136
|
+
return undefined;
|
|
137
|
+
}
|
|
138
|
+
export function finalAsyncIterator(source, onFinal) {
|
|
139
|
+
const iterator = source[Symbol.asyncIterator]();
|
|
140
|
+
let isDone = false;
|
|
141
|
+
const stream = {
|
|
142
|
+
[Symbol.asyncIterator]() {
|
|
143
|
+
return stream;
|
|
144
|
+
},
|
|
145
|
+
async next() {
|
|
146
|
+
const result = await iterator.next();
|
|
147
|
+
if (result.done && isDone === false) {
|
|
148
|
+
isDone = true;
|
|
149
|
+
onFinal();
|
|
150
|
+
}
|
|
151
|
+
return result;
|
|
152
|
+
},
|
|
153
|
+
async return() {
|
|
154
|
+
var _a;
|
|
155
|
+
const promise = (_a = iterator.return) === null || _a === void 0 ? void 0 : _a.call(iterator);
|
|
156
|
+
if (isDone === false) {
|
|
157
|
+
isDone = true;
|
|
158
|
+
onFinal();
|
|
159
|
+
}
|
|
160
|
+
return promise ? await promise : { done: true, value: undefined };
|
|
161
|
+
},
|
|
162
|
+
async throw(error) {
|
|
163
|
+
var _a;
|
|
164
|
+
const promise = (_a = iterator.throw) === null || _a === void 0 ? void 0 : _a.call(iterator);
|
|
165
|
+
if (promise) {
|
|
166
|
+
return await promise;
|
|
167
|
+
}
|
|
168
|
+
// if the source has no throw method we just re-throw error
|
|
169
|
+
// usually throw is not called anyways
|
|
170
|
+
throw error;
|
|
171
|
+
},
|
|
172
|
+
};
|
|
173
|
+
return stream;
|
|
174
|
+
}
|
|
175
|
+
export function errorAsyncIterator(source, onError) {
|
|
176
|
+
const iterator = source[Symbol.asyncIterator]();
|
|
177
|
+
const stream = {
|
|
178
|
+
[Symbol.asyncIterator]() {
|
|
179
|
+
return stream;
|
|
180
|
+
},
|
|
181
|
+
async next() {
|
|
182
|
+
try {
|
|
183
|
+
return await iterator.next();
|
|
184
|
+
}
|
|
185
|
+
catch (error) {
|
|
186
|
+
onError(error);
|
|
187
|
+
return { done: true, value: undefined };
|
|
188
|
+
}
|
|
189
|
+
},
|
|
190
|
+
async return() {
|
|
191
|
+
var _a;
|
|
192
|
+
const promise = (_a = iterator.return) === null || _a === void 0 ? void 0 : _a.call(iterator);
|
|
193
|
+
return promise ? await promise : { done: true, value: undefined };
|
|
194
|
+
},
|
|
195
|
+
async throw(error) {
|
|
196
|
+
var _a;
|
|
197
|
+
const promise = (_a = iterator.throw) === null || _a === void 0 ? void 0 : _a.call(iterator);
|
|
198
|
+
if (promise) {
|
|
199
|
+
return await promise;
|
|
200
|
+
}
|
|
201
|
+
// if the source has no throw method we just re-throw error
|
|
202
|
+
// usually throw is not called anyways
|
|
203
|
+
throw error;
|
|
204
|
+
},
|
|
205
|
+
};
|
|
206
|
+
return stream;
|
|
207
|
+
}
|
package/package.json
CHANGED
|
@@ -1,16 +1,16 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@envelop/core",
|
|
3
|
-
"version": "2.4.0-alpha-
|
|
3
|
+
"version": "2.4.0-alpha-05dbec7.0",
|
|
4
4
|
"sideEffects": false,
|
|
5
5
|
"peerDependencies": {
|
|
6
6
|
"graphql": "^14.0.0 || ^15.0.0 || ^16.0.0"
|
|
7
7
|
},
|
|
8
8
|
"dependencies": {
|
|
9
|
-
"@envelop/types": "2.
|
|
9
|
+
"@envelop/types": "2.3.0-alpha-05dbec7.0"
|
|
10
10
|
},
|
|
11
11
|
"repository": {
|
|
12
12
|
"type": "git",
|
|
13
|
-
"url": "https://github.com/
|
|
13
|
+
"url": "https://github.com/n1ru4l/envelop.git",
|
|
14
14
|
"directory": "packages/core"
|
|
15
15
|
},
|
|
16
16
|
"keywords": [
|
|
@@ -24,21 +24,42 @@
|
|
|
24
24
|
],
|
|
25
25
|
"author": "Dotan Simha <dotansimha@gmail.com>",
|
|
26
26
|
"license": "MIT",
|
|
27
|
-
"main": "index.js",
|
|
28
|
-
"module": "index.
|
|
29
|
-
"typings": "index.d.ts",
|
|
27
|
+
"main": "cjs/index.js",
|
|
28
|
+
"module": "esm/index.js",
|
|
29
|
+
"typings": "typings/index.d.ts",
|
|
30
30
|
"typescript": {
|
|
31
|
-
"definition": "index.d.ts"
|
|
31
|
+
"definition": "typings/index.d.ts"
|
|
32
32
|
},
|
|
33
|
+
"type": "module",
|
|
33
34
|
"exports": {
|
|
34
35
|
".": {
|
|
35
|
-
"require":
|
|
36
|
-
|
|
36
|
+
"require": {
|
|
37
|
+
"types": "./typings/index.d.ts",
|
|
38
|
+
"default": "./cjs/index.js"
|
|
39
|
+
},
|
|
40
|
+
"import": {
|
|
41
|
+
"types": "./typings/index.d.ts",
|
|
42
|
+
"default": "./esm/index.js"
|
|
43
|
+
},
|
|
44
|
+
"default": {
|
|
45
|
+
"types": "./typings/index.d.ts",
|
|
46
|
+
"default": "./esm/index.js"
|
|
47
|
+
}
|
|
37
48
|
},
|
|
38
49
|
"./*": {
|
|
39
|
-
"require":
|
|
40
|
-
|
|
50
|
+
"require": {
|
|
51
|
+
"types": "./typings/*.d.ts",
|
|
52
|
+
"default": "./cjs/*.js"
|
|
53
|
+
},
|
|
54
|
+
"import": {
|
|
55
|
+
"types": "./typings/*.d.ts",
|
|
56
|
+
"default": "./esm/*.js"
|
|
57
|
+
},
|
|
58
|
+
"default": {
|
|
59
|
+
"types": "./typings/*.d.ts",
|
|
60
|
+
"default": "./esm/*.js"
|
|
61
|
+
}
|
|
41
62
|
},
|
|
42
63
|
"./package.json": "./package.json"
|
|
43
64
|
}
|
|
44
|
-
}
|
|
65
|
+
}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { GetEnvelopedFn, ComposeContext, Plugin } from '@envelop/types';
|
|
2
|
-
import { PluginOrDisabledPlugin } from './enable-if';
|
|
2
|
+
import { PluginOrDisabledPlugin } from './enable-if.js';
|
|
3
3
|
export declare function envelop<PluginsType extends Plugin<any>[]>(options: {
|
|
4
4
|
plugins: Array<PluginOrDisabledPlugin>;
|
|
5
5
|
enableInternalTracing?: boolean;
|
|
File without changes
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
export * from '@envelop/types';
|
|
2
|
+
export * from './create.js';
|
|
3
|
+
export * from './utils.js';
|
|
4
|
+
export * from './plugins/use-envelop.js';
|
|
5
|
+
export * from './plugins/use-logger.js';
|
|
6
|
+
export * from './plugins/use-timing.js';
|
|
7
|
+
export * from './plugins/use-schema.js';
|
|
8
|
+
export * from './plugins/use-error-handler.js';
|
|
9
|
+
export * from './plugins/use-extend-context.js';
|
|
10
|
+
export * from './plugins/use-payload-formatter.js';
|
|
11
|
+
export * from './plugins/use-masked-errors.js';
|
|
12
|
+
export * from './plugins/use-immediate-introspection.js';
|
|
13
|
+
export * from './enable-if.js';
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|