/*
 * The version of the OpenAPI document: v68
 * Contact: developer-experience@adyen.com
 *
 * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech).
 * https://openapi-generator.tech
 * Do not edit this class manually.
 */


export * from './address';
export * from './amount';
export * from './bankAccount';
export * from './card';
export * from './fraudCheckResult';
export * from './fraudResult';
export * from './fundSource';
export * from './modifyRequest';
export * from './modifyResponse';
export * from './name';
export * from './payoutRequest';
export * from './payoutResponse';
export * from './recurring';
export * from './responseAdditionalData3DSecure';
export * from './responseAdditionalDataBillingAddress';
export * from './responseAdditionalDataCard';
export * from './responseAdditionalDataCommon';
export * from './responseAdditionalDataInstallments';
export * from './responseAdditionalDataNetworkTokens';
export * from './responseAdditionalDataOpi';
export * from './responseAdditionalDataSepa';
export * from './serviceError';
export * from './storeDetailAndSubmitRequest';
export * from './storeDetailAndSubmitResponse';
export * from './storeDetailRequest';
export * from './storeDetailResponse';
export * from './submitRequest';
export * from './submitResponse';


import { Address } from './address';
import { Amount } from './amount';
import { BankAccount } from './bankAccount';
import { Card } from './card';
import { FraudCheckResult } from './fraudCheckResult';
import { FraudResult } from './fraudResult';
import { FundSource } from './fundSource';
import { ModifyRequest } from './modifyRequest';
import { ModifyResponse } from './modifyResponse';
import { Name } from './name';
import { PayoutRequest } from './payoutRequest';
import { PayoutResponse } from './payoutResponse';
import { Recurring } from './recurring';
import { ResponseAdditionalData3DSecure } from './responseAdditionalData3DSecure';
import { ResponseAdditionalDataBillingAddress } from './responseAdditionalDataBillingAddress';
import { ResponseAdditionalDataCard } from './responseAdditionalDataCard';
import { ResponseAdditionalDataCommon } from './responseAdditionalDataCommon';
import { ResponseAdditionalDataInstallments } from './responseAdditionalDataInstallments';
import { ResponseAdditionalDataNetworkTokens } from './responseAdditionalDataNetworkTokens';
import { ResponseAdditionalDataOpi } from './responseAdditionalDataOpi';
import { ResponseAdditionalDataSepa } from './responseAdditionalDataSepa';
import { ServiceError } from './serviceError';
import { StoreDetailAndSubmitRequest } from './storeDetailAndSubmitRequest';
import { StoreDetailAndSubmitResponse } from './storeDetailAndSubmitResponse';
import { StoreDetailRequest } from './storeDetailRequest';
import { StoreDetailResponse } from './storeDetailResponse';
import { SubmitRequest } from './submitRequest';
import { SubmitResponse } from './submitResponse';

/* tslint:disable:no-unused-variable */
let primitives = [
                    "string",
                    "boolean",
                    "double",
                    "integer",
                    "long",
                    "float",
                    "number",
                    "any"
                 ];

let enumsMap: {[index: string]: any} = {
        "PayoutRequest.ShopperInteractionEnum": PayoutRequest.ShopperInteractionEnum,
        "PayoutResponse.ResultCodeEnum": PayoutResponse.ResultCodeEnum,
        "Recurring.ContractEnum": Recurring.ContractEnum,
        "Recurring.TokenServiceEnum": Recurring.TokenServiceEnum,
        "ResponseAdditionalDataCommon.FraudResultTypeEnum": ResponseAdditionalDataCommon.FraudResultTypeEnum,
        "ResponseAdditionalDataCommon.RecurringProcessingModelEnum": ResponseAdditionalDataCommon.RecurringProcessingModelEnum,
        "StoreDetailAndSubmitRequest.EntityTypeEnum": StoreDetailAndSubmitRequest.EntityTypeEnum,
        "StoreDetailRequest.EntityTypeEnum": StoreDetailRequest.EntityTypeEnum,
        "SubmitRequest.EntityTypeEnum": SubmitRequest.EntityTypeEnum,
}

let typeMap: {[index: string]: any} = {
    "Address": Address,
    "Amount": Amount,
    "BankAccount": BankAccount,
    "Card": Card,
    "FraudCheckResult": FraudCheckResult,
    "FraudResult": FraudResult,
    "FundSource": FundSource,
    "ModifyRequest": ModifyRequest,
    "ModifyResponse": ModifyResponse,
    "Name": Name,
    "PayoutRequest": PayoutRequest,
    "PayoutResponse": PayoutResponse,
    "Recurring": Recurring,
    "ResponseAdditionalData3DSecure": ResponseAdditionalData3DSecure,
    "ResponseAdditionalDataBillingAddress": ResponseAdditionalDataBillingAddress,
    "ResponseAdditionalDataCard": ResponseAdditionalDataCard,
    "ResponseAdditionalDataCommon": ResponseAdditionalDataCommon,
    "ResponseAdditionalDataInstallments": ResponseAdditionalDataInstallments,
    "ResponseAdditionalDataNetworkTokens": ResponseAdditionalDataNetworkTokens,
    "ResponseAdditionalDataOpi": ResponseAdditionalDataOpi,
    "ResponseAdditionalDataSepa": ResponseAdditionalDataSepa,
    "ServiceError": ServiceError,
    "StoreDetailAndSubmitRequest": StoreDetailAndSubmitRequest,
    "StoreDetailAndSubmitResponse": StoreDetailAndSubmitResponse,
    "StoreDetailRequest": StoreDetailRequest,
    "StoreDetailResponse": StoreDetailResponse,
    "SubmitRequest": SubmitRequest,
    "SubmitResponse": SubmitResponse,
}

export class ObjectSerializer {
    public static findCorrectType(data: any, expectedType: string) {
        if (data == undefined) {
            return expectedType;
        } else if (primitives.indexOf(expectedType.toLowerCase()) !== -1) {
            return expectedType;
        } else if (expectedType === "Date") {
            return expectedType;
        } else {
            if (enumsMap[expectedType]) {
                return expectedType;
            }

            if (!typeMap[expectedType]) {
                return expectedType; // w/e we don't know the type
            }

            // Check the discriminator
            let discriminatorProperty = typeMap[expectedType].discriminator;
            if (discriminatorProperty == null) {
                return expectedType; // the type does not have a discriminator. use it.
            } else {
                if (data[discriminatorProperty]) {
                    var discriminatorType = data[discriminatorProperty];
                    if(typeMap[discriminatorType]){
                        return discriminatorType; // use the type given in the discriminator
                    } else {
                        return expectedType; // discriminator did not map to a type
                    }
                } else {
                    return expectedType; // discriminator was not present (or an empty string)
                }
            }
        }
    }

    public static serialize(data: any, type: string) {
        if (data == undefined) {
            return data;
        } else if (primitives.indexOf(type.toLowerCase()) !== -1) {
            return data;
        } else if (type.lastIndexOf("Array<", 0) === 0) { // string.startsWith pre es6
            let subType: string = type.replace("Array<", ""); // Array<Type> => Type>
            subType = subType.substring(0, subType.length - 1); // Type> => Type
            let transformedData: any[] = [];
            for (let index = 0; index < data.length; index++) {
                let datum = data[index];
                transformedData.push(ObjectSerializer.serialize(datum, subType));
            }
            return transformedData;
        } else if (type === "Date") {
            return data.toISOString();
        } else if (type === "SaleToAcquirerData") {
            const dataString = JSON.stringify(data);
            return Buffer.from(dataString).toString("base64");
        } else {
            if (enumsMap[type]) {
                return data;
            }
            if (!typeMap[type]) { // in case we dont know the type
                return data;
            }

            // Get the actual type of this object
            type = this.findCorrectType(data, type);

            // get the map for the correct type.
            let attributeTypes = typeMap[type].getAttributeTypeMap();
            let instance: {[index: string]: any} = {};
            for (let index = 0; index < attributeTypes.length; index++) {
                let attributeType = attributeTypes[index];
                instance[attributeType.baseName] = ObjectSerializer.serialize(data[attributeType.name], attributeType.type);
            }
            return instance;
        }
    }

    public static deserialize(data: any, type: string) {
        // polymorphism may change the actual type.
        type = ObjectSerializer.findCorrectType(data, type);
        if (data == undefined) {
            return data;
        } else if (primitives.indexOf(type.toLowerCase()) !== -1) {
            return data;
        } else if (type.lastIndexOf("Array<", 0) === 0) { // string.startsWith pre es6
            let subType: string = type.replace("Array<", ""); // Array<Type> => Type>
            subType = subType.substring(0, subType.length - 1); // Type> => Type
            let transformedData: any[] = [];
            for (let index = 0; index < data.length; index++) {
                let datum = data[index];
                transformedData.push(ObjectSerializer.deserialize(datum, subType));
            }
            return transformedData;
        } else if (type === "Date") {
            return new Date(data);
        } else {
            if (enumsMap[type]) {// is Enum
                return data;
            }

            if (!typeMap[type]) { // dont know the type
                return data;
            }
            let instance = new typeMap[type]();
            let attributeTypes = typeMap[type].getAttributeTypeMap();
            for (let index = 0; index < attributeTypes.length; index++) {
                let attributeType = attributeTypes[index];
                instance[attributeType.name] = ObjectSerializer.deserialize(data[attributeType.baseName], attributeType.type);
            }
            return instance;
        }
    }
}
