All files validation.js

86.67% Statements 26/30
50% Branches 4/8
100% Functions 3/3
86.67% Lines 26/30

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93    1x 1x 1x 1x 1x 1x 1x     754x 754x       754x               754x         754x 754x 754x   754x                 754x 754x                               754x     754x 754x 754x     754x 754x       754x   754x                             1x      
'use strict';
 
const { execute } = require( './execute.js' );
const { Invariants } = require( './Invariants.js' );
const { ZWrapper } = require( './ZWrapper.js' );
const { quoteZObject, makeWrappedResultEnvelope } = require( './utils.js' );
const { error, makeErrorInNormalForm } = require( '../function-schemata/javascript/src/error.js' );
const { convertZListToItemArray, findFunctionIdentity } = require( '../function-schemata/javascript/src/utils.js' );
const { EmptyFrame } = require( './frame.js' );
 
function createValidatorZ7( Z8, ...Z1s ) {
	const argumentDeclarations = convertZListToItemArray( Z8.Z8K1 || [] );
	Iif ( argumentDeclarations.length !== Z1s.length ) {
		// TODO (T2926668): Call BUILTIN_FUNCTION_CALL_VALIDATOR_ on result to
		// avoid argument mismatches.
	}
	const result = {
		Z1K1: {
			Z1K1: 'Z9',
			Z9K1: 'Z7'
		},
		Z7K1: Z8
	};
	// TBD: Possibly arrange to convert to ZWrapper here instead of below
	for ( const argument of argumentDeclarations ) {
		// TODO (T315232): Eliminate this ZWrapper copy if possible.
		// Currently this separate copy of the ZWrapper object avoids allowing
		// resolution to affect the original object. Whether this is desirable
		// (or whether, alternatively, we are ok with that side-effect) is TBD.
		let nextZ1 = Z1s.shift();
		nextZ1 = nextZ1.copy();
		result[ argument.Z17K2.Z6K1 ] = nextZ1;
	}
	return ZWrapper.create(
		result,
		// Use an empty scope for the outer object, the nested objects should already have their own
		// scope, if any.
		new EmptyFrame()
	);
}
 
async function runValidationFunction( Z8, invariants, ...Z1s ) {
	const validatorZ7 = createValidatorZ7( Z8, ...Z1s );
	return await execute( validatorZ7, invariants, /* doValidate= */ false );
}
 
/**
 * Dynamically validates the Z1/Object against its type validator and returns
 * an array of Z5/Error.
 *
 * TODO (T302750): Find a better way to handle this than two separate "runTypeValidator"
 * functions.
 *
 * @param {Object} Z1 the Z1/Object
 * @param {Object} Z4 the type ZObject
 * @param {Invariants} invariants evaluator, resolver: invariants preserved over all function calls
 * @return {Array} an array of Z5/Error
 */
async function runTypeValidatorDynamic( Z1, Z4, invariants ) {
	Iif ( !invariants.orchestratorConfig.doValidate ) {
		return makeWrappedResultEnvelope( Z1, null );
	}
	await ( Z4.resolveEphemeral( [ 'Z4K3' ], invariants, /* ignoreList= */ null, /* resolveInternals= */ false ) );
	const validationFunction = Z4.getNameEphemeral( 'Z4K3' );
	const validationIdentity = findFunctionIdentity( validationFunction );
 
	// TODO (T327872): Oh, when to quote!
	const genericSchemaValidatorZID = 'Z831';
	Iif ( validationIdentity.Z9K1 === genericSchemaValidatorZID ) {
		Z1 = quoteZObject( Z1 );
	}
 
	try {
		// TODO (T296681): Catch errors when async functions reject.
		return await runValidationFunction( validationFunction, invariants, Z1 );
	} catch ( e ) {
		invariants.logger.log( 'error',
			{
				message: `Error dynamically running built-in type validator. Error: ${ e }.`,
				requestId: invariants.requestId
			}
		);
		return makeWrappedResultEnvelope(
			null,
			makeErrorInNormalForm( error.zid_not_found, [ validationIdentity.Z9K1 ] )
		);
	}
}
 
module.exports = {
	runTypeValidatorDynamic
};