@envelop/core 1.5.0 → 1.6.3
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/index.js +78 -41
- package/index.mjs +67 -33
- package/package.json +2 -2
- package/traced-orchestrator.d.ts +3 -1
- package/utils.d.ts +16 -1
package/index.js
CHANGED
|
@@ -158,6 +158,37 @@ function getExecuteArgs(args) {
|
|
|
158
158
|
* Utility function for making a execute function that handles polymorphic arguments.
|
|
159
159
|
*/
|
|
160
160
|
const makeExecute = (executeFn) => ((...polyArgs) => executeFn(getExecuteArgs(polyArgs)));
|
|
161
|
+
/**
|
|
162
|
+
* Returns true if the provided object implements the AsyncIterator protocol via
|
|
163
|
+
* implementing a `Symbol.asyncIterator` method.
|
|
164
|
+
*
|
|
165
|
+
* Source: https://github.com/graphql/graphql-js/blob/main/src/jsutils/isAsyncIterable.ts
|
|
166
|
+
*/
|
|
167
|
+
function isAsyncIterable(maybeAsyncIterable) {
|
|
168
|
+
return (typeof maybeAsyncIterable === 'object' &&
|
|
169
|
+
maybeAsyncIterable != null &&
|
|
170
|
+
typeof maybeAsyncIterable[Symbol.asyncIterator] === 'function');
|
|
171
|
+
}
|
|
172
|
+
/**
|
|
173
|
+
* A utility function for handling `onExecuteDone` hook result, for simplifying the handling of AsyncIterable returned from `execute`.
|
|
174
|
+
*
|
|
175
|
+
* @param payload The payload send to `onExecuteDone` hook function
|
|
176
|
+
* @param fn The handler to be executed on each result
|
|
177
|
+
* @returns a subscription for streamed results, or undefined in case of an non-async
|
|
178
|
+
*/
|
|
179
|
+
function handleStreamOrSingleExecutionResult(payload, fn) {
|
|
180
|
+
if (isAsyncIterable(payload.result)) {
|
|
181
|
+
return { onNext: fn };
|
|
182
|
+
}
|
|
183
|
+
else {
|
|
184
|
+
fn({
|
|
185
|
+
args: payload.args,
|
|
186
|
+
result: payload.result,
|
|
187
|
+
setResult: payload.setResult,
|
|
188
|
+
});
|
|
189
|
+
return undefined;
|
|
190
|
+
}
|
|
191
|
+
}
|
|
161
192
|
async function* finalAsyncIterator(asyncIterable, onFinal) {
|
|
162
193
|
try {
|
|
163
194
|
yield* asyncIterable;
|
|
@@ -444,7 +475,7 @@ function createEnvelopOrchestrator(plugins) {
|
|
|
444
475
|
}
|
|
445
476
|
}
|
|
446
477
|
}
|
|
447
|
-
if (onNextHandler.length &&
|
|
478
|
+
if (onNextHandler.length && isAsyncIterable(result)) {
|
|
448
479
|
result = mapAsyncIterator(result, async (result) => {
|
|
449
480
|
for (const onNext of onNextHandler) {
|
|
450
481
|
await onNext({
|
|
@@ -456,14 +487,14 @@ function createEnvelopOrchestrator(plugins) {
|
|
|
456
487
|
return result;
|
|
457
488
|
});
|
|
458
489
|
}
|
|
459
|
-
if (onEndHandler.length &&
|
|
490
|
+
if (onEndHandler.length && isAsyncIterable(result)) {
|
|
460
491
|
result = finalAsyncIterator(result, () => {
|
|
461
492
|
for (const onEnd of onEndHandler) {
|
|
462
493
|
onEnd();
|
|
463
494
|
}
|
|
464
495
|
});
|
|
465
496
|
}
|
|
466
|
-
if (subscribeErrorHandlers.length &&
|
|
497
|
+
if (subscribeErrorHandlers.length && isAsyncIterable(result)) {
|
|
467
498
|
result = errorAsyncIterator(result, err => {
|
|
468
499
|
let error = err;
|
|
469
500
|
for (const handler of subscribeErrorHandlers) {
|
|
@@ -525,10 +556,10 @@ function createEnvelopOrchestrator(plugins) {
|
|
|
525
556
|
if (onResolversHandlers.length) {
|
|
526
557
|
context[resolversHooksSymbol] = onResolversHandlers;
|
|
527
558
|
}
|
|
528
|
-
result = await executeFn({
|
|
559
|
+
result = (await executeFn({
|
|
529
560
|
...args,
|
|
530
561
|
contextValue: context,
|
|
531
|
-
});
|
|
562
|
+
}));
|
|
532
563
|
const onNextHandler = [];
|
|
533
564
|
const onEndHandler = [];
|
|
534
565
|
for (const afterCb of afterCalls) {
|
|
@@ -548,19 +579,21 @@ function createEnvelopOrchestrator(plugins) {
|
|
|
548
579
|
}
|
|
549
580
|
}
|
|
550
581
|
}
|
|
551
|
-
if (onNextHandler.length &&
|
|
582
|
+
if (onNextHandler.length && isAsyncIterable(result)) {
|
|
552
583
|
result = mapAsyncIterator(result, async (result) => {
|
|
553
584
|
for (const onNext of onNextHandler) {
|
|
554
585
|
await onNext({
|
|
555
586
|
args: args,
|
|
556
587
|
result,
|
|
557
|
-
setResult: newResult =>
|
|
588
|
+
setResult: newResult => {
|
|
589
|
+
result = newResult;
|
|
590
|
+
},
|
|
558
591
|
});
|
|
559
592
|
}
|
|
560
593
|
return result;
|
|
561
594
|
});
|
|
562
595
|
}
|
|
563
|
-
if (onEndHandler.length &&
|
|
596
|
+
if (onEndHandler.length && isAsyncIterable(result)) {
|
|
564
597
|
result = finalAsyncIterator(result, () => {
|
|
565
598
|
for (const onEnd of onEndHandler) {
|
|
566
599
|
onEnd();
|
|
@@ -595,25 +628,27 @@ function createEnvelopOrchestrator(plugins) {
|
|
|
595
628
|
};
|
|
596
629
|
}
|
|
597
630
|
|
|
598
|
-
|
|
599
|
-
const
|
|
600
|
-
const
|
|
601
|
-
const
|
|
602
|
-
|
|
603
|
-
|
|
631
|
+
var _a;
|
|
632
|
+
const getTimestamp = typeof globalThis !== 'undefined' && ((_a = globalThis === null || globalThis === void 0 ? void 0 : globalThis.performance) === null || _a === void 0 ? void 0 : _a.now) ? () => performance.now() : () => Date.now();
|
|
633
|
+
const measure = () => {
|
|
634
|
+
const start = getTimestamp();
|
|
635
|
+
return () => {
|
|
636
|
+
const end = getTimestamp();
|
|
637
|
+
return start - end;
|
|
638
|
+
};
|
|
604
639
|
};
|
|
640
|
+
const tracingSymbol = Symbol('envelopTracing');
|
|
605
641
|
function traceOrchestrator(orchestrator) {
|
|
606
642
|
const createTracer = (name, ctx) => {
|
|
607
|
-
const
|
|
643
|
+
const end = measure();
|
|
608
644
|
return () => {
|
|
609
|
-
|
|
610
|
-
ctx._envelopTracing[name] = time;
|
|
645
|
+
ctx[tracingSymbol][name] = end();
|
|
611
646
|
};
|
|
612
647
|
};
|
|
613
648
|
return {
|
|
614
649
|
...orchestrator,
|
|
615
650
|
init: (ctx = {}) => {
|
|
616
|
-
ctx
|
|
651
|
+
ctx[tracingSymbol] = ctx[tracingSymbol] || {};
|
|
617
652
|
const done = createTracer('init', ctx || {});
|
|
618
653
|
try {
|
|
619
654
|
return orchestrator.init(ctx);
|
|
@@ -623,7 +658,7 @@ function traceOrchestrator(orchestrator) {
|
|
|
623
658
|
}
|
|
624
659
|
},
|
|
625
660
|
parse: (ctx = {}) => {
|
|
626
|
-
ctx
|
|
661
|
+
ctx[tracingSymbol] = ctx[tracingSymbol] || {};
|
|
627
662
|
const actualFn = orchestrator.parse(ctx);
|
|
628
663
|
return (...args) => {
|
|
629
664
|
const done = createTracer('parse', ctx);
|
|
@@ -636,7 +671,7 @@ function traceOrchestrator(orchestrator) {
|
|
|
636
671
|
};
|
|
637
672
|
},
|
|
638
673
|
validate: (ctx = {}) => {
|
|
639
|
-
ctx
|
|
674
|
+
ctx[tracingSymbol] = ctx[tracingSymbol] || {};
|
|
640
675
|
const actualFn = orchestrator.validate(ctx);
|
|
641
676
|
return (...args) => {
|
|
642
677
|
const done = createTracer('validate', ctx);
|
|
@@ -667,11 +702,11 @@ function traceOrchestrator(orchestrator) {
|
|
|
667
702
|
try {
|
|
668
703
|
const result = await orchestrator.execute(args);
|
|
669
704
|
done();
|
|
670
|
-
if (!
|
|
705
|
+
if (!isAsyncIterable(result)) {
|
|
671
706
|
result.extensions = result.extensions || {};
|
|
672
707
|
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
|
673
708
|
// @ts-ignore GraphQL.js types contextValue as unknown
|
|
674
|
-
result.extensions.envelopTracing = args.contextValue
|
|
709
|
+
result.extensions.envelopTracing = args.contextValue[tracingSymbol];
|
|
675
710
|
}
|
|
676
711
|
else {
|
|
677
712
|
// eslint-disable-next-line no-console
|
|
@@ -795,23 +830,23 @@ const useLogger = (rawOptions = DEFAULT_OPTIONS) => {
|
|
|
795
830
|
};
|
|
796
831
|
};
|
|
797
832
|
|
|
798
|
-
const HR_TO_NS
|
|
799
|
-
const NS_TO_MS
|
|
833
|
+
const HR_TO_NS = 1e9;
|
|
834
|
+
const NS_TO_MS = 1e6;
|
|
800
835
|
const DEFAULT_OPTIONS$1 = {
|
|
801
836
|
onExecutionMeasurement: (args, timing) => console.log(`Operation execution "${args.operationName}" done in ${timing.ms}ms`),
|
|
802
|
-
onSubscriptionMeasurement: (args, timing) => console.log(`Operation
|
|
837
|
+
onSubscriptionMeasurement: (args, timing) => console.log(`Operation subscription "${args.operationName}" done in ${timing.ms}ms`),
|
|
803
838
|
onParsingMeasurement: (source, timing) => console.log(`Parsing "${source}" done in ${timing.ms}ms`),
|
|
804
839
|
onValidationMeasurement: (document, timing) => { var _a, _b; return console.log(`Validation "${((_b = (_a = graphql.getOperationAST(document)) === null || _a === void 0 ? void 0 : _a.name) === null || _b === void 0 ? void 0 : _b.value) || '-'}" done in ${timing.ms}ms`); },
|
|
805
840
|
onResolverMeasurement: (info, timing) => console.log(`\tResolver of "${info.parentType.toString()}.${info.fieldName}" done in ${timing.ms}ms`),
|
|
806
841
|
onContextBuildingMeasurement: (timing) => console.log(`Context building done in ${timing.ms}ms`),
|
|
807
842
|
};
|
|
808
|
-
const deltaFrom
|
|
843
|
+
const deltaFrom = (hrtime) => {
|
|
809
844
|
const delta = process.hrtime(hrtime);
|
|
810
|
-
const ns = delta[0] * HR_TO_NS
|
|
845
|
+
const ns = delta[0] * HR_TO_NS + delta[1];
|
|
811
846
|
return {
|
|
812
847
|
ns,
|
|
813
848
|
get ms() {
|
|
814
|
-
return ns / NS_TO_MS
|
|
849
|
+
return ns / NS_TO_MS;
|
|
815
850
|
},
|
|
816
851
|
};
|
|
817
852
|
};
|
|
@@ -828,7 +863,7 @@ const useTiming = (rawOptions) => {
|
|
|
828
863
|
}
|
|
829
864
|
const contextStartTime = process.hrtime();
|
|
830
865
|
return () => {
|
|
831
|
-
options.onContextBuildingMeasurement(deltaFrom
|
|
866
|
+
options.onContextBuildingMeasurement(deltaFrom(contextStartTime));
|
|
832
867
|
};
|
|
833
868
|
};
|
|
834
869
|
}
|
|
@@ -842,7 +877,7 @@ const useTiming = (rawOptions) => {
|
|
|
842
877
|
}
|
|
843
878
|
const parseStartTime = process.hrtime();
|
|
844
879
|
return () => {
|
|
845
|
-
options.onParsingMeasurement(params.source, deltaFrom
|
|
880
|
+
options.onParsingMeasurement(params.source, deltaFrom(parseStartTime));
|
|
846
881
|
};
|
|
847
882
|
};
|
|
848
883
|
}
|
|
@@ -853,7 +888,7 @@ const useTiming = (rawOptions) => {
|
|
|
853
888
|
}
|
|
854
889
|
const validateStartTime = process.hrtime();
|
|
855
890
|
return () => {
|
|
856
|
-
options.onValidationMeasurement(params.documentAST, deltaFrom
|
|
891
|
+
options.onValidationMeasurement(params.documentAST, deltaFrom(validateStartTime));
|
|
857
892
|
};
|
|
858
893
|
};
|
|
859
894
|
}
|
|
@@ -866,12 +901,12 @@ const useTiming = (rawOptions) => {
|
|
|
866
901
|
const executeStartTime = process.hrtime();
|
|
867
902
|
return {
|
|
868
903
|
onExecuteDone: () => {
|
|
869
|
-
options.onExecutionMeasurement(args, deltaFrom
|
|
904
|
+
options.onExecutionMeasurement(args, deltaFrom(executeStartTime));
|
|
870
905
|
},
|
|
871
906
|
onResolverCalled: ({ info }) => {
|
|
872
907
|
const resolverStartTime = process.hrtime();
|
|
873
908
|
return () => {
|
|
874
|
-
options.onResolverMeasurement(info, deltaFrom
|
|
909
|
+
options.onResolverMeasurement(info, deltaFrom(resolverStartTime));
|
|
875
910
|
};
|
|
876
911
|
},
|
|
877
912
|
};
|
|
@@ -885,7 +920,7 @@ const useTiming = (rawOptions) => {
|
|
|
885
920
|
const executeStartTime = process.hrtime();
|
|
886
921
|
return {
|
|
887
922
|
onExecuteDone: () => {
|
|
888
|
-
options.onExecutionMeasurement(args, deltaFrom
|
|
923
|
+
options.onExecutionMeasurement(args, deltaFrom(executeStartTime));
|
|
889
924
|
},
|
|
890
925
|
};
|
|
891
926
|
};
|
|
@@ -900,12 +935,12 @@ const useTiming = (rawOptions) => {
|
|
|
900
935
|
const subscribeStartTime = process.hrtime();
|
|
901
936
|
return {
|
|
902
937
|
onSubscribeResult: () => {
|
|
903
|
-
options.onSubscriptionMeasurement && options.onSubscriptionMeasurement(args, deltaFrom
|
|
938
|
+
options.onSubscriptionMeasurement && options.onSubscriptionMeasurement(args, deltaFrom(subscribeStartTime));
|
|
904
939
|
},
|
|
905
940
|
onResolverCalled: ({ info }) => {
|
|
906
941
|
const resolverStartTime = process.hrtime();
|
|
907
942
|
return () => {
|
|
908
|
-
options.onResolverMeasurement && options.onResolverMeasurement(info, deltaFrom
|
|
943
|
+
options.onResolverMeasurement && options.onResolverMeasurement(info, deltaFrom(resolverStartTime));
|
|
909
944
|
};
|
|
910
945
|
},
|
|
911
946
|
};
|
|
@@ -919,7 +954,7 @@ const useTiming = (rawOptions) => {
|
|
|
919
954
|
const subscribeStartTime = process.hrtime();
|
|
920
955
|
return {
|
|
921
956
|
onSubscribeResult: () => {
|
|
922
|
-
options.onSubscriptionMeasurement && options.onSubscriptionMeasurement(args, deltaFrom
|
|
957
|
+
options.onSubscriptionMeasurement && options.onSubscriptionMeasurement(args, deltaFrom(subscribeStartTime));
|
|
923
958
|
},
|
|
924
959
|
};
|
|
925
960
|
};
|
|
@@ -963,7 +998,7 @@ const useErrorHandler = (errorHandler) => ({
|
|
|
963
998
|
const handleResult = makeHandleResult(errorHandler);
|
|
964
999
|
return {
|
|
965
1000
|
onExecuteDone(payload) {
|
|
966
|
-
return
|
|
1001
|
+
return handleStreamOrSingleExecutionResult(payload, handleResult);
|
|
967
1002
|
},
|
|
968
1003
|
};
|
|
969
1004
|
},
|
|
@@ -986,7 +1021,7 @@ const usePayloadFormatter = (formatter) => ({
|
|
|
986
1021
|
const handleResult = makeHandleResult$1(formatter);
|
|
987
1022
|
return {
|
|
988
1023
|
onExecuteDone(payload) {
|
|
989
|
-
return
|
|
1024
|
+
return handleStreamOrSingleExecutionResult(payload, handleResult);
|
|
990
1025
|
},
|
|
991
1026
|
};
|
|
992
1027
|
},
|
|
@@ -1026,14 +1061,14 @@ const useMaskedErrors = (opts) => {
|
|
|
1026
1061
|
onExecute() {
|
|
1027
1062
|
return {
|
|
1028
1063
|
onExecuteDone(payload) {
|
|
1029
|
-
return
|
|
1064
|
+
return handleStreamOrSingleExecutionResult(payload, handleResult);
|
|
1030
1065
|
},
|
|
1031
1066
|
};
|
|
1032
1067
|
},
|
|
1033
1068
|
onSubscribe() {
|
|
1034
1069
|
return {
|
|
1035
1070
|
onSubscribeResult(payload) {
|
|
1036
|
-
return
|
|
1071
|
+
return handleStreamOrSingleExecutionResult(payload, handleResult);
|
|
1037
1072
|
},
|
|
1038
1073
|
onSubscribeError({ error, setError }) {
|
|
1039
1074
|
setError(formatError(error, message));
|
|
@@ -1059,6 +1094,8 @@ exports.envelopIsIntrospectionSymbol = envelopIsIntrospectionSymbol;
|
|
|
1059
1094
|
exports.errorAsyncIterator = errorAsyncIterator;
|
|
1060
1095
|
exports.finalAsyncIterator = finalAsyncIterator;
|
|
1061
1096
|
exports.formatError = formatError;
|
|
1097
|
+
exports.handleStreamOrSingleExecutionResult = handleStreamOrSingleExecutionResult;
|
|
1098
|
+
exports.isAsyncIterable = isAsyncIterable;
|
|
1062
1099
|
exports.isIntrospectionDocument = isIntrospectionDocument;
|
|
1063
1100
|
exports.isIntrospectionOperation = isIntrospectionOperation;
|
|
1064
1101
|
exports.isIntrospectionOperationString = isIntrospectionOperationString;
|
package/index.mjs
CHANGED
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
import { isAsyncIterable, handleStreamOrSingleExecutionResult } from '@envelop/types';
|
|
2
1
|
export * from '@envelop/types';
|
|
3
2
|
import { isIntrospectionType, isObjectType, defaultFieldResolver, Kind, visit, BREAK, parse, specifiedRules, validate, execute, subscribe, GraphQLSchema, getOperationAST, GraphQLError } from 'graphql';
|
|
4
3
|
|
|
@@ -155,6 +154,37 @@ function getExecuteArgs(args) {
|
|
|
155
154
|
* Utility function for making a execute function that handles polymorphic arguments.
|
|
156
155
|
*/
|
|
157
156
|
const makeExecute = (executeFn) => ((...polyArgs) => executeFn(getExecuteArgs(polyArgs)));
|
|
157
|
+
/**
|
|
158
|
+
* Returns true if the provided object implements the AsyncIterator protocol via
|
|
159
|
+
* implementing a `Symbol.asyncIterator` method.
|
|
160
|
+
*
|
|
161
|
+
* Source: https://github.com/graphql/graphql-js/blob/main/src/jsutils/isAsyncIterable.ts
|
|
162
|
+
*/
|
|
163
|
+
function isAsyncIterable(maybeAsyncIterable) {
|
|
164
|
+
return (typeof maybeAsyncIterable === 'object' &&
|
|
165
|
+
maybeAsyncIterable != null &&
|
|
166
|
+
typeof maybeAsyncIterable[Symbol.asyncIterator] === 'function');
|
|
167
|
+
}
|
|
168
|
+
/**
|
|
169
|
+
* A utility function for handling `onExecuteDone` hook result, for simplifying the handling of AsyncIterable returned from `execute`.
|
|
170
|
+
*
|
|
171
|
+
* @param payload The payload send to `onExecuteDone` hook function
|
|
172
|
+
* @param fn The handler to be executed on each result
|
|
173
|
+
* @returns a subscription for streamed results, or undefined in case of an non-async
|
|
174
|
+
*/
|
|
175
|
+
function handleStreamOrSingleExecutionResult(payload, fn) {
|
|
176
|
+
if (isAsyncIterable(payload.result)) {
|
|
177
|
+
return { onNext: fn };
|
|
178
|
+
}
|
|
179
|
+
else {
|
|
180
|
+
fn({
|
|
181
|
+
args: payload.args,
|
|
182
|
+
result: payload.result,
|
|
183
|
+
setResult: payload.setResult,
|
|
184
|
+
});
|
|
185
|
+
return undefined;
|
|
186
|
+
}
|
|
187
|
+
}
|
|
158
188
|
async function* finalAsyncIterator(asyncIterable, onFinal) {
|
|
159
189
|
try {
|
|
160
190
|
yield* asyncIterable;
|
|
@@ -522,10 +552,10 @@ function createEnvelopOrchestrator(plugins) {
|
|
|
522
552
|
if (onResolversHandlers.length) {
|
|
523
553
|
context[resolversHooksSymbol] = onResolversHandlers;
|
|
524
554
|
}
|
|
525
|
-
result = await executeFn({
|
|
555
|
+
result = (await executeFn({
|
|
526
556
|
...args,
|
|
527
557
|
contextValue: context,
|
|
528
|
-
});
|
|
558
|
+
}));
|
|
529
559
|
const onNextHandler = [];
|
|
530
560
|
const onEndHandler = [];
|
|
531
561
|
for (const afterCb of afterCalls) {
|
|
@@ -551,7 +581,9 @@ function createEnvelopOrchestrator(plugins) {
|
|
|
551
581
|
await onNext({
|
|
552
582
|
args: args,
|
|
553
583
|
result,
|
|
554
|
-
setResult: newResult =>
|
|
584
|
+
setResult: newResult => {
|
|
585
|
+
result = newResult;
|
|
586
|
+
},
|
|
555
587
|
});
|
|
556
588
|
}
|
|
557
589
|
return result;
|
|
@@ -592,25 +624,27 @@ function createEnvelopOrchestrator(plugins) {
|
|
|
592
624
|
};
|
|
593
625
|
}
|
|
594
626
|
|
|
595
|
-
|
|
596
|
-
const
|
|
597
|
-
const
|
|
598
|
-
const
|
|
599
|
-
|
|
600
|
-
|
|
627
|
+
var _a;
|
|
628
|
+
const getTimestamp = typeof globalThis !== 'undefined' && ((_a = globalThis === null || globalThis === void 0 ? void 0 : globalThis.performance) === null || _a === void 0 ? void 0 : _a.now) ? () => performance.now() : () => Date.now();
|
|
629
|
+
const measure = () => {
|
|
630
|
+
const start = getTimestamp();
|
|
631
|
+
return () => {
|
|
632
|
+
const end = getTimestamp();
|
|
633
|
+
return start - end;
|
|
634
|
+
};
|
|
601
635
|
};
|
|
636
|
+
const tracingSymbol = Symbol('envelopTracing');
|
|
602
637
|
function traceOrchestrator(orchestrator) {
|
|
603
638
|
const createTracer = (name, ctx) => {
|
|
604
|
-
const
|
|
639
|
+
const end = measure();
|
|
605
640
|
return () => {
|
|
606
|
-
|
|
607
|
-
ctx._envelopTracing[name] = time;
|
|
641
|
+
ctx[tracingSymbol][name] = end();
|
|
608
642
|
};
|
|
609
643
|
};
|
|
610
644
|
return {
|
|
611
645
|
...orchestrator,
|
|
612
646
|
init: (ctx = {}) => {
|
|
613
|
-
ctx
|
|
647
|
+
ctx[tracingSymbol] = ctx[tracingSymbol] || {};
|
|
614
648
|
const done = createTracer('init', ctx || {});
|
|
615
649
|
try {
|
|
616
650
|
return orchestrator.init(ctx);
|
|
@@ -620,7 +654,7 @@ function traceOrchestrator(orchestrator) {
|
|
|
620
654
|
}
|
|
621
655
|
},
|
|
622
656
|
parse: (ctx = {}) => {
|
|
623
|
-
ctx
|
|
657
|
+
ctx[tracingSymbol] = ctx[tracingSymbol] || {};
|
|
624
658
|
const actualFn = orchestrator.parse(ctx);
|
|
625
659
|
return (...args) => {
|
|
626
660
|
const done = createTracer('parse', ctx);
|
|
@@ -633,7 +667,7 @@ function traceOrchestrator(orchestrator) {
|
|
|
633
667
|
};
|
|
634
668
|
},
|
|
635
669
|
validate: (ctx = {}) => {
|
|
636
|
-
ctx
|
|
670
|
+
ctx[tracingSymbol] = ctx[tracingSymbol] || {};
|
|
637
671
|
const actualFn = orchestrator.validate(ctx);
|
|
638
672
|
return (...args) => {
|
|
639
673
|
const done = createTracer('validate', ctx);
|
|
@@ -668,7 +702,7 @@ function traceOrchestrator(orchestrator) {
|
|
|
668
702
|
result.extensions = result.extensions || {};
|
|
669
703
|
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
|
670
704
|
// @ts-ignore GraphQL.js types contextValue as unknown
|
|
671
|
-
result.extensions.envelopTracing = args.contextValue
|
|
705
|
+
result.extensions.envelopTracing = args.contextValue[tracingSymbol];
|
|
672
706
|
}
|
|
673
707
|
else {
|
|
674
708
|
// eslint-disable-next-line no-console
|
|
@@ -792,23 +826,23 @@ const useLogger = (rawOptions = DEFAULT_OPTIONS) => {
|
|
|
792
826
|
};
|
|
793
827
|
};
|
|
794
828
|
|
|
795
|
-
const HR_TO_NS
|
|
796
|
-
const NS_TO_MS
|
|
829
|
+
const HR_TO_NS = 1e9;
|
|
830
|
+
const NS_TO_MS = 1e6;
|
|
797
831
|
const DEFAULT_OPTIONS$1 = {
|
|
798
832
|
onExecutionMeasurement: (args, timing) => console.log(`Operation execution "${args.operationName}" done in ${timing.ms}ms`),
|
|
799
|
-
onSubscriptionMeasurement: (args, timing) => console.log(`Operation
|
|
833
|
+
onSubscriptionMeasurement: (args, timing) => console.log(`Operation subscription "${args.operationName}" done in ${timing.ms}ms`),
|
|
800
834
|
onParsingMeasurement: (source, timing) => console.log(`Parsing "${source}" done in ${timing.ms}ms`),
|
|
801
835
|
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`); },
|
|
802
836
|
onResolverMeasurement: (info, timing) => console.log(`\tResolver of "${info.parentType.toString()}.${info.fieldName}" done in ${timing.ms}ms`),
|
|
803
837
|
onContextBuildingMeasurement: (timing) => console.log(`Context building done in ${timing.ms}ms`),
|
|
804
838
|
};
|
|
805
|
-
const deltaFrom
|
|
839
|
+
const deltaFrom = (hrtime) => {
|
|
806
840
|
const delta = process.hrtime(hrtime);
|
|
807
|
-
const ns = delta[0] * HR_TO_NS
|
|
841
|
+
const ns = delta[0] * HR_TO_NS + delta[1];
|
|
808
842
|
return {
|
|
809
843
|
ns,
|
|
810
844
|
get ms() {
|
|
811
|
-
return ns / NS_TO_MS
|
|
845
|
+
return ns / NS_TO_MS;
|
|
812
846
|
},
|
|
813
847
|
};
|
|
814
848
|
};
|
|
@@ -825,7 +859,7 @@ const useTiming = (rawOptions) => {
|
|
|
825
859
|
}
|
|
826
860
|
const contextStartTime = process.hrtime();
|
|
827
861
|
return () => {
|
|
828
|
-
options.onContextBuildingMeasurement(deltaFrom
|
|
862
|
+
options.onContextBuildingMeasurement(deltaFrom(contextStartTime));
|
|
829
863
|
};
|
|
830
864
|
};
|
|
831
865
|
}
|
|
@@ -839,7 +873,7 @@ const useTiming = (rawOptions) => {
|
|
|
839
873
|
}
|
|
840
874
|
const parseStartTime = process.hrtime();
|
|
841
875
|
return () => {
|
|
842
|
-
options.onParsingMeasurement(params.source, deltaFrom
|
|
876
|
+
options.onParsingMeasurement(params.source, deltaFrom(parseStartTime));
|
|
843
877
|
};
|
|
844
878
|
};
|
|
845
879
|
}
|
|
@@ -850,7 +884,7 @@ const useTiming = (rawOptions) => {
|
|
|
850
884
|
}
|
|
851
885
|
const validateStartTime = process.hrtime();
|
|
852
886
|
return () => {
|
|
853
|
-
options.onValidationMeasurement(params.documentAST, deltaFrom
|
|
887
|
+
options.onValidationMeasurement(params.documentAST, deltaFrom(validateStartTime));
|
|
854
888
|
};
|
|
855
889
|
};
|
|
856
890
|
}
|
|
@@ -863,12 +897,12 @@ const useTiming = (rawOptions) => {
|
|
|
863
897
|
const executeStartTime = process.hrtime();
|
|
864
898
|
return {
|
|
865
899
|
onExecuteDone: () => {
|
|
866
|
-
options.onExecutionMeasurement(args, deltaFrom
|
|
900
|
+
options.onExecutionMeasurement(args, deltaFrom(executeStartTime));
|
|
867
901
|
},
|
|
868
902
|
onResolverCalled: ({ info }) => {
|
|
869
903
|
const resolverStartTime = process.hrtime();
|
|
870
904
|
return () => {
|
|
871
|
-
options.onResolverMeasurement(info, deltaFrom
|
|
905
|
+
options.onResolverMeasurement(info, deltaFrom(resolverStartTime));
|
|
872
906
|
};
|
|
873
907
|
},
|
|
874
908
|
};
|
|
@@ -882,7 +916,7 @@ const useTiming = (rawOptions) => {
|
|
|
882
916
|
const executeStartTime = process.hrtime();
|
|
883
917
|
return {
|
|
884
918
|
onExecuteDone: () => {
|
|
885
|
-
options.onExecutionMeasurement(args, deltaFrom
|
|
919
|
+
options.onExecutionMeasurement(args, deltaFrom(executeStartTime));
|
|
886
920
|
},
|
|
887
921
|
};
|
|
888
922
|
};
|
|
@@ -897,12 +931,12 @@ const useTiming = (rawOptions) => {
|
|
|
897
931
|
const subscribeStartTime = process.hrtime();
|
|
898
932
|
return {
|
|
899
933
|
onSubscribeResult: () => {
|
|
900
|
-
options.onSubscriptionMeasurement && options.onSubscriptionMeasurement(args, deltaFrom
|
|
934
|
+
options.onSubscriptionMeasurement && options.onSubscriptionMeasurement(args, deltaFrom(subscribeStartTime));
|
|
901
935
|
},
|
|
902
936
|
onResolverCalled: ({ info }) => {
|
|
903
937
|
const resolverStartTime = process.hrtime();
|
|
904
938
|
return () => {
|
|
905
|
-
options.onResolverMeasurement && options.onResolverMeasurement(info, deltaFrom
|
|
939
|
+
options.onResolverMeasurement && options.onResolverMeasurement(info, deltaFrom(resolverStartTime));
|
|
906
940
|
};
|
|
907
941
|
},
|
|
908
942
|
};
|
|
@@ -916,7 +950,7 @@ const useTiming = (rawOptions) => {
|
|
|
916
950
|
const subscribeStartTime = process.hrtime();
|
|
917
951
|
return {
|
|
918
952
|
onSubscribeResult: () => {
|
|
919
|
-
options.onSubscriptionMeasurement && options.onSubscriptionMeasurement(args, deltaFrom
|
|
953
|
+
options.onSubscriptionMeasurement && options.onSubscriptionMeasurement(args, deltaFrom(subscribeStartTime));
|
|
920
954
|
},
|
|
921
955
|
};
|
|
922
956
|
};
|
|
@@ -1040,4 +1074,4 @@ const useMaskedErrors = (opts) => {
|
|
|
1040
1074
|
};
|
|
1041
1075
|
};
|
|
1042
1076
|
|
|
1043
|
-
export { DEFAULT_ERROR_MESSAGE, EnvelopError, enableIf, envelop, envelopIsIntrospectionSymbol, errorAsyncIterator, finalAsyncIterator, formatError, isIntrospectionDocument, isIntrospectionOperation, isIntrospectionOperationString, isOperationDefinition, isPluginEnabled, makeExecute, makeSubscribe, mapAsyncIterator, useAsyncSchema, useEnvelop, useErrorHandler, useExtendContext, useLazyLoadedSchema, useLogger, useMaskedErrors, usePayloadFormatter, useSchema, useTiming };
|
|
1077
|
+
export { DEFAULT_ERROR_MESSAGE, EnvelopError, enableIf, envelop, envelopIsIntrospectionSymbol, errorAsyncIterator, finalAsyncIterator, formatError, handleStreamOrSingleExecutionResult, isAsyncIterable, isIntrospectionDocument, isIntrospectionOperation, isIntrospectionOperationString, isOperationDefinition, isPluginEnabled, makeExecute, makeSubscribe, mapAsyncIterator, useAsyncSchema, useEnvelop, useErrorHandler, useExtendContext, useLazyLoadedSchema, useLogger, useMaskedErrors, usePayloadFormatter, useSchema, useTiming };
|
package/package.json
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@envelop/core",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.6.3",
|
|
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": "1.
|
|
9
|
+
"@envelop/types": "1.5.1"
|
|
10
10
|
},
|
|
11
11
|
"repository": {
|
|
12
12
|
"type": "git",
|
package/traced-orchestrator.d.ts
CHANGED
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
import { ArbitraryObject } from '@envelop/types';
|
|
2
2
|
import { EnvelopOrchestrator } from './orchestrator';
|
|
3
|
+
declare const tracingSymbol: unique symbol;
|
|
3
4
|
export declare function traceOrchestrator<TInitialContext extends ArbitraryObject, TPluginsContext extends ArbitraryObject>(orchestrator: EnvelopOrchestrator<TInitialContext, TPluginsContext>): EnvelopOrchestrator<TInitialContext & {
|
|
4
|
-
|
|
5
|
+
[tracingSymbol]?: {};
|
|
5
6
|
}, TPluginsContext>;
|
|
7
|
+
export {};
|
package/utils.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { ASTNode, DocumentNode, OperationDefinitionNode, Source, ExecutionResult, SubscriptionArgs, ExecutionArgs } from 'graphql';
|
|
2
|
-
import { AsyncIterableIteratorOrValue, ExecuteFunction, SubscribeFunction, PromiseOrValue } from '@envelop/types';
|
|
2
|
+
import { AsyncIterableIteratorOrValue, ExecuteFunction, SubscribeFunction, PromiseOrValue, DefaultContext, OnExecuteDoneEventPayload, OnExecuteDoneHookResult, OnExecuteDoneHookResultOnNextHook } from '@envelop/types';
|
|
3
3
|
export declare const envelopIsIntrospectionSymbol: unique symbol;
|
|
4
4
|
export declare function isOperationDefinition(def: ASTNode): def is OperationDefinitionNode;
|
|
5
5
|
export declare function isIntrospectionOperation(operation: OperationDefinitionNode): boolean;
|
|
@@ -14,5 +14,20 @@ export declare function mapAsyncIterator<TInput, TOutput = TInput>(asyncIterable
|
|
|
14
14
|
* Utility function for making a execute function that handles polymorphic arguments.
|
|
15
15
|
*/
|
|
16
16
|
export declare const makeExecute: (executeFn: (args: ExecutionArgs) => PromiseOrValue<AsyncIterableIteratorOrValue<ExecutionResult>>) => ExecuteFunction;
|
|
17
|
+
/**
|
|
18
|
+
* Returns true if the provided object implements the AsyncIterator protocol via
|
|
19
|
+
* implementing a `Symbol.asyncIterator` method.
|
|
20
|
+
*
|
|
21
|
+
* Source: https://github.com/graphql/graphql-js/blob/main/src/jsutils/isAsyncIterable.ts
|
|
22
|
+
*/
|
|
23
|
+
export declare function isAsyncIterable<TType>(maybeAsyncIterable: unknown): maybeAsyncIterable is AsyncIterable<TType>;
|
|
24
|
+
/**
|
|
25
|
+
* A utility function for handling `onExecuteDone` hook result, for simplifying the handling of AsyncIterable returned from `execute`.
|
|
26
|
+
*
|
|
27
|
+
* @param payload The payload send to `onExecuteDone` hook function
|
|
28
|
+
* @param fn The handler to be executed on each result
|
|
29
|
+
* @returns a subscription for streamed results, or undefined in case of an non-async
|
|
30
|
+
*/
|
|
31
|
+
export declare function handleStreamOrSingleExecutionResult<ContextType = DefaultContext>(payload: OnExecuteDoneEventPayload<ContextType>, fn: OnExecuteDoneHookResultOnNextHook<ContextType>): void | OnExecuteDoneHookResult<ContextType>;
|
|
17
32
|
export declare function finalAsyncIterator<TInput>(asyncIterable: AsyncIterable<TInput>, onFinal: () => void): AsyncIterableIterator<TInput>;
|
|
18
33
|
export declare function errorAsyncIterator<TInput>(asyncIterable: AsyncIterable<TInput>, onError: (err: unknown) => void): AsyncIterableIterator<TInput>;
|