Source: editing/transactionItem.js

let TransactionExecutor = require('./transactionExecutor');
let Guid = require('./../math/guid');
let XMLMapper = require('xml-mapping');

/**
 * Класс TransactionItem
 */
class TransactionItem {
    /**
     * Конструктор TransactionItem
     * @param params {object} - параметры
     * @param params.action {string} - содержание транзакции (json)
     * @param params.executor {object} - исполнитель транзакции
     * @param params.className {string} - имя объекта в хранилище
     * @param params.layerId {layerId} - идентификатор слоя
     * @param params.sourceObject {DataSource} - объект источника данных
     */
    constructor(params) {
        const executor = (new TransactionExecutor()).getDefaultExecutor();
        this.guid = Guid.createGUID();
        this.state = false;
        this.action = params.action;
        this.executor = params.executor || executor;
        this.className = params.className;
        this.layerId = params.layerId;
        this.sourceObject = params.sourceObject;
        this.feature = params.feature;
        this.transactionType = params.transactionType;
    }

    /**
     * Выполнение транзакции
     * @returns {Promise.<*>}
     */
    async execute() {
        let self = this;
        let executor = self.executor;
        let action = self.action;

        let executeResult;
        let responseData;

        let feature = self.feature;
        let featureId = feature.getId();

        //todo разобраться со switch и обработкой ответа
        try {
            executeResult = await executor(action);
            responseData = XMLMapper.load(executeResult.data, {
                nested: true,
                specialChar: "_"
            });
            switch (self.transactionType) {
                case "insert":
                    featureId = responseData.wfs_TransactionResponse.wfs_InsertResults.wfs_Feature.ogc_FeatureId.fid;
                    break;
                case "update":
                    featureId = feature.getId();
                    break;
                case "delete":
                    featureId = feature.getId();
                    break;
                default:
                    featureId = feature.getId();
                    break;
            }

            this.state = true;
        }
        catch (e) {
            this.state = false;
        }

        if (self.state === true) self.parentAction({featureId: featureId});

        return {
            state: this.state,
            result: executeResult,
            data: responseData,
            featureId: featureId
        }
    }

    parentAction(params) {
        let self = this;
        let sourceObject = self.sourceObject;
        let feature = self.feature;
        let featureId = params.featureId;
        sourceObject.updateFeatures({featureId: featureId, feature: feature});
    }

    /**
     * Задание исполнителя транзакции
     * @param {TransactionExecutor} executor - объект, выполняющий транзакцию
     */
    setExecutor(executor) {
        this.executor = executor;
        return this;
    }

    /**
     * Изменение состояния транзакци
     * @param state
     */
    setState(state) {
        this.state = state;
    }

    /**
     * Получение состояния транзакции
     * @returns {boolean} - текущее состояние (true/false)
     */
    getState() {
        return this.state;
    }

    /**
     * Получение id транзакции
     * @returns {string} - guid транзакции
     */
    getId() {
        return this.guid;
    }

    /**
     * Сериализация содержимого транзакции
     * @returns {string} - json-string транзакции
     */
    serialize() {
        let self = this;
        let data = {
            guid: self.guid,
            state: self.state,
            action: self.action,
            className: self.className,
            layerId: self.layerId
        };
        return JSON.stringify(data);
    }

    /**
     * Восстановление транзакции
     * @param data
     */
    parse(data) {
        let parsedData = JSON.parse(data);
        this.guid = parsedData.guid;
        this.state = parsedData.state;
        this.action = parsedData.action;
        this.className = parsedData.className;
        this.layerId = parsedData.layerId;
        return parsedData;
    }
}

module.exports = TransactionItem;