"use strict";
// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License. See License.txt in the project root for license information.
Object.defineProperty(exports, "__esModule", { value: true });
exports.CdmOperationAddArtifactAttribute = void 0;
const internal_1 = require("../../internal");
const CdmAttributeGroupReference_1 = require("../CdmAttributeGroupReference");
const CdmEntityAttributeDefinition_1 = require("../CdmEntityAttributeDefinition");
const CdmTypeAttributeDefinition_1 = require("../CdmTypeAttributeDefinition");
/**
 * Class to handle AddArtifactAttribute operations
 */
class CdmOperationAddArtifactAttribute extends internal_1.CdmOperationBase {
    constructor(ctx) {
        super(ctx);
        this.TAG = CdmOperationAddArtifactAttribute.name;
        this.objectType = internal_1.cdmObjectType.operationAddArtifactAttributeDef;
        this.type = internal_1.cdmOperationType.addArtifactAttribute;
    }
    /**
     * @inheritdoc
     */
    copy(resOpt, host) {
        if (!resOpt) {
            resOpt = new internal_1.resolveOptions(this, this.ctx.corpus.defaultResolutionDirectives);
        }
        const copy = !host ? new CdmOperationAddArtifactAttribute(this.ctx) : host;
        copy.newAttribute = this.newAttribute ? this.newAttribute.copy(resOpt) : undefined;
        copy.insertAtTop = this.insertAtTop;
        this.copyProj(resOpt, copy);
        return copy;
    }
    /**
     * @inheritdoc
     */
    getName() {
        return 'operationAddArtifactAttribute';
    }
    /**
     * @inheritdoc
     */
    getObjectType() {
        return internal_1.cdmObjectType.operationAddArtifactAttributeDef;
    }
    /**
     * @inheritdoc
     */
    validate() {
        const missingFields = [];
        if (!this.newAttribute) {
            missingFields.push('newAttribute');
        }
        if (missingFields.length > 0) {
            internal_1.Logger.error(this.ctx, this.TAG, this.validate.name, this.atCorpusPath, internal_1.cdmLogCode.ErrValdnIntegrityCheckFailure, this.atCorpusPath, missingFields.map((s) => `'${s}'`).join(', '));
            return false;
        }
        return true;
    }
    /**
     * @inheritdoc
     */
    visit(pathFrom, preChildren, postChildren) {
        const path = this.fetchDeclaredPath(pathFrom);
        if (preChildren && preChildren(this, path)) {
            return false;
        }
        if (this.newAttribute !== undefined && this.newAttribute.visit(`${path}/newAttribute/`, preChildren, postChildren)) {
            return true;
        }
        if (postChildren && postChildren(this, path)) {
            return true;
        }
        return false;
    }
    /**
     * @inheritdoc
     * @internal
     */
    appendProjectionAttributeState(projCtx, projOutputSet, attrCtx) {
        if (this.insertAtTop != true) {
            this.addAllPreviousAttributeStates(projCtx, projOutputSet);
            this.addNewArtifactAttributeState(projCtx, projOutputSet, attrCtx);
        }
        else {
            this.addNewArtifactAttributeState(projCtx, projOutputSet, attrCtx);
            this.addAllPreviousAttributeStates(projCtx, projOutputSet);
        }
        return projOutputSet;
    }
    addNewArtifactAttributeState(projCtx, projOutputSet, attrCtx) {
        // Create a new attribute context for the operation
        const attrCtxOpAddAttrGroupParam = {
            under: attrCtx,
            type: internal_1.cdmAttributeContextType.operationAddArtifactAttribute,
            name: `operation/index${this.index}/${this.getName()}`
        };
        const attrCtxOpAddArtifactAttr = internal_1.CdmAttributeContext.createChildUnder(projCtx.projectionDirective.resOpt, attrCtxOpAddAttrGroupParam);
        if (this.newAttribute instanceof CdmTypeAttributeDefinition_1.CdmTypeAttributeDefinition) {
            // Create a new attribute context for the new artifact attribute we will create
            const attrCtxAttrGroupParam = {
                under: attrCtxOpAddArtifactAttr,
                type: internal_1.cdmAttributeContextType.addedAttributeNewArtifact,
                name: this.newAttribute.fetchObjectDefinitionName()
            };
            const attrCtxNewAttr = internal_1.CdmAttributeContext.createChildUnder(projCtx.projectionDirective.resOpt, attrCtxAttrGroupParam);
            const newResAttr = internal_1.CdmOperationBase.createNewResolvedAttribute(projCtx, attrCtxNewAttr, this.newAttribute);
            // Create a new projection attribute state for the new artifact attribute and add it to the output set
            // There is no previous state for the newly created attribute
            const newPAS = new internal_1.ProjectionAttributeState(projOutputSet.ctx);
            newPAS.currentResolvedAttribute = newResAttr;
            projOutputSet.add(newPAS);
        }
        else if (this.newAttribute instanceof CdmEntityAttributeDefinition_1.CdmEntityAttributeDefinition || this.newAttribute instanceof CdmAttributeGroupReference_1.CdmAttributeGroupReference) {
            const typeStr = this.newAttribute instanceof CdmEntityAttributeDefinition_1.CdmEntityAttributeDefinition ? 'an entity attribute' : 'an attribute group';
            internal_1.Logger.warning(this.ctx, this.TAG, this.appendProjectionAttributeState.name, this.atCorpusPath, internal_1.cdmLogCode.WarnProjAddArtifactAttrNotSupported, typeStr);
        }
        else {
            internal_1.Logger.warning(this.ctx, this.TAG, this.appendProjectionAttributeState.name, this.atCorpusPath, internal_1.cdmLogCode.ErrProjUnsupportedSource, this.newAttribute.objectType.toString(), this.getName());
        }
        return projOutputSet;
    }
    /**
     * Pass through all the input projection attribute states if there are any.
     */
    addAllPreviousAttributeStates(projCtx, projOutputSet) {
        // Pass through all the input projection attribute states if there are any
        for (const currentPAS of projCtx.currentAttributeStateSet.states) {
            projOutputSet.add(currentPAS);
        }
    }
}
exports.CdmOperationAddArtifactAttribute = CdmOperationAddArtifactAttribute;
//# sourceMappingURL=CdmOperationAddArtifactAttribute.js.map