import { binaryOptions } from '../built-in-options/index.js';
import JDLEnums from './jdl-enums.js';
import JDLRelationships from './jdl-relationships.js';
import JDLOptions from './jdl-options.js';
import JDLAigcs from './jdl-aigcs.js';
export default class JDLObject {
    applications;
    deployments;
    entities;
    enums;
    relationships;
    options;
    aigcs;
    constructor() {
        this.applications = {};
        this.deployments = {};
        this.entities = {};
        this.enums = new JDLEnums();
        this.relationships = new JDLRelationships();
        this.options = new JDLOptions();
        this.aigcs = new JDLAigcs();
    }
    getOptions() {
        return this.options.getOptions();
    }
    addApplication(application) {
        if (!application) {
            throw new Error("Can't add nil application.");
        }
        const baseName = application.getConfigurationOptionValue('baseName');
        this.applications[baseName] = application;
    }
    getApplicationQuantity() {
        return Object.keys(this.applications).length;
    }
    getApplication(applicationName) {
        if (!applicationName) {
            return undefined;
        }
        return this.applications[applicationName];
    }
    getApplications() {
        return Object.values(this.applications);
    }
    forEachApplication(passedFunction) {
        if (!passedFunction) {
            return;
        }
        Object.keys(this.applications).forEach(applicationName => {
            const application = this.applications[applicationName];
            passedFunction(application);
        });
    }
    addDeployment(deployment) {
        if (!deployment) {
            throw new Error("Can't add nil deployment.");
        }
        this.deployments[deployment.deploymentType] = deployment;
    }
    getDeploymentQuantity() {
        return Object.keys(this.deployments).length;
    }
    forEachDeployment(passedFunction) {
        if (!passedFunction) {
            return;
        }
        Object.keys(this.deployments).forEach((deploymentName, index, array) => {
            const deployment = this.deployments[deploymentName];
            passedFunction(deployment, index, array);
        });
    }
    addEntity(entity) {
        if (!entity) {
            throw new Error("Can't add nil entity.");
        }
        this.entities[entity.name] = entity;
    }
    getEntity(entityName) {
        if (!entityName) {
            throw new Error('An entity name must be passed so as to be retrieved.');
        }
        return this.entities[entityName];
    }
    getEntities() {
        return Object.values(this.entities);
    }
    getEntityQuantity() {
        return this.getEntityNames().length;
    }
    getEntityNames() {
        return Object.keys(this.entities);
    }
    forEachEntity(passedFunction) {
        if (!passedFunction) {
            return;
        }
        Object.keys(this.entities).forEach((entityName, index, array) => {
            const entity = this.entities[entityName];
            passedFunction(entity, index, array);
        });
    }
    addEnum(enumToAdd) {
        if (!enumToAdd) {
            throw new Error("Can't add nil enum.");
        }
        this.enums.add(enumToAdd);
    }
    hasEnum(enumName) {
        return this.enums.has(enumName);
    }
    getEnum(enumName) {
        return this.enums.get(enumName);
    }
    getEnumQuantity() {
        return this.enums.size();
    }
    forEachEnum(passedFunction) {
        if (!passedFunction) {
            return;
        }
        this.enums.forEach(jdlEnum => {
            passedFunction(jdlEnum);
        });
    }
    addRelationship(relationship) {
        if (!relationship) {
            throw new Error("Can't add nil relationship.");
        }
        this.relationships.add(relationship);
    }
    addAigc(aigc) {
        if (!aigc) {
            throw new Error("Can't add nil aigc.");
        }
        this.aigcs.add(aigc);
    }
    getRelationshipQuantity(applicationName) {
        if (!applicationName) {
            return this.relationships.size();
        }
        const applicationEntityNames = this.applications[applicationName].entityNames;
        let count = 0;
        this.relationships.forEach(relationship => {
            if (applicationEntityNames.has(relationship.from) || applicationEntityNames.has(relationship.to)) {
                count++;
            }
        });
        return count;
    }
    getAigcQuantity(applicationName) {
        if (!applicationName) {
            return this.aigcs.size();
        }
        const applicationEntityNames = this.applications[applicationName].entityNames;
        let count = 0;
        this.aigcs.forEach(aigc => {
            if (applicationEntityNames.has(aigc.from)) {
                count++;
            }
        });
        return count;
    }
    forEachRelationship(passedFunction) {
        if (!passedFunction) {
            return;
        }
        this.relationships.forEach(jdlRelationship => {
            passedFunction(jdlRelationship);
        });
    }
    forEachAigc(passedFunction) {
        if (!passedFunction) {
            return;
        }
        this.aigcs.forEach(aigc => {
            passedFunction(aigc);
        });
    }
    getRelationships() {
        return this.relationships.toArray();
    }
    getAigcs() {
        return this.aigcs.toArray();
    }
    addOption(option) {
        if (!option?.getType) {
            throw new Error("Can't add nil option.");
        }
        this.options.addOption(option);
    }
    getOptionsForName(optionName) {
        return this.options.getOptionsForName(optionName);
    }
    forEachOption(passedFunction) {
        if (!passedFunction) {
            return;
        }
        this.options.forEach(passedFunction);
    }
    hasOption(optionName) {
        if (!optionName) {
            return false;
        }
        return this.options.has(optionName);
    }
    isEntityInMicroservice(entityName) {
        const options = this.getOptionsForName(binaryOptions.Options.MICROSERVICE);
        return options.some(option => option.entityNames.has('*') || option.entityNames.has(entityName));
    }
    getOptionQuantity() {
        return this.options.size();
    }
    toString() {
        return [
            applicationsToString(this.applications),
            deploymentsToString(this.deployments),
            entitiesToString(this.entities),
            this.enums.toString(),
            relationshipsToString(this.relationships),
            optionsToString(this.options),
            aigcsToString(this.aigcs),
        ]
            .map(section => section.trim())
            .filter(Boolean)
            .join('\n\n')
            .concat('\n');
    }
}
function applicationsToString(applications) {
    return Object.values(applications)
        .map(application => application.toString())
        .join('\n');
}
function deploymentsToString(deployments) {
    return Object.values(deployments)
        .map(deployment => deployment.toString())
        .join('\n');
}
function entitiesToString(entities) {
    return Object.values(entities)
        .map(entity => entity.toString())
        .join('\n');
}
function relationshipsToString(relationships) {
    return relationships.toString();
}
function aigcsToString(aigcs) {
    return aigcs.toString();
}
function optionsToString(options) {
    return options.toString();
}
