validateNDepthEntities = function(collection, entitiesAndRoles, intentsCollection) {
    (collection || []).forEach(child => {
        if(child.instanceOf) {
            let baseEntityFound = entitiesAndRoles.find(i => i.name == child.instanceOf);
            if (!baseEntityFound) {
                let errorMsg = `Invalid child entity definition found. No definition for "${child.instanceOf}" in child entity definition "${child.context.definition}".`;
                const error = BuildDiagnostic({
                    message: errorMsg,
                    line: child.context.line
                });
                throw (new exception(retCode.errorCode.INVALID_INPUT, error.toString(), [error]));
            }
            // base type can only be a list or regex or prebuilt.
            if (![EntityTypeEnum.LIST, EntityTypeEnum.REGEX, EntityTypeEnum.PREBUILT, EntityTypeEnum.ML].includes(baseEntityFound.type)) {
                let errorMsg = `Invalid child entity definition found. "${child.instanceOf}" is of type "${baseEntityFound.type}" in child entity definition "${child.context.definition}". Child cannot be only be an instance of "${EntityTypeEnum.LIST}, ${EntityTypeEnum.REGEX} or ${EntityTypeEnum.PREBUILT}.`;
                const error = BuildDiagnostic({
                    message: errorMsg,
                    line: child.context.line
                });
                throw (new exception(retCode.errorCode.INVALID_INPUT, error.toString(), [error]));
            }

        }

        if (child.features) {
            let featureHandled = false;
            (child.features || []).forEach((feature, idx) => {
                if (typeof feature === "object") return;
                featureHandled = false;
                feature = feature.replace(/["']/gi, '');
                let featureExists = entitiesAndRoles.find(i => (i.name == feature || i.name == `${feature}(interchangeable)`));
                if (featureExists) {
                    // is feature phrase list?
                    if (featureExists.type == EntityTypeEnum.PHRASELIST) {
                        child.features[idx] = new helperClass.featureToModel(feature, featureProperties.phraseListFeature);
                        featureHandled = true;
                    } else if (featureExists.type == EntityTypeEnum.PATTERNANY) {
                        let errorMsg = `Invalid child entity definition found. "${feature}" is of type "${EntityTypeEnum.PATTERNANY}" in child entity definition "${child.context.definition}". Child cannot include a usesFeature of type "${EntityTypeEnum.PATTERNANY}".`;
                        const error = BuildDiagnostic({
                            message: errorMsg,
                            line: child.context.line
                        });
                        throw (new exception(retCode.errorCode.INVALID_INPUT, error.toString(), [error]));
                    } else {
                        child.features[idx] = new helperClass.modelToFeature(feature, featureProperties.entityFeatureToModel[featureExists.type]);
                        featureHandled = true;
                    }
                }
                if (!featureHandled) {
                    // find feature as intent
                    let intentFeatureExists = intentsCollection.find(i => i.name == feature);
                    if (intentFeatureExists) {
                        child.features[idx] = new helperClass.modelToFeature(feature, featureProperties.intentFeatureToModel);
                        featureHandled = true;
                    } else {
                        let errorMsg = `Invalid child entity definition found. No definition found for "${feature}" in child entity definition "${child.context.definition}". Features must be defined before they can be added to a child.`;
                        const error = BuildDiagnostic({
                            message: errorMsg,
                            line: child.context.line
                        });
                        throw (new exception(retCode.errorCode.INVALID_INPUT, error.toString(), [error]));
                    }
                }
            })
        }

        if (child.children) {
            validateNDepthEntities(child.children, entitiesAndRoles, intentsCollection);
        }

        if (child.context) {
            delete child.context
        }

        if (child.features === "") {
            delete child.features
        }
    })
}
Helper function to validate and update nDepth entities
@param {Object[]} collection 
@param {Object[]} entitiesAndRoles 
@param {Object[]} intentsCollection