Map Reduce script to set Access Token in Custom record from FedEX/UPS

A map reduces script that sets access token value from FedEx and UPS to a custom record in NetSuite.

 (https, record, search, log, encode) => {
        /**
        * @description Get the configuration details of the FedEx and UPS from the custom record.
        * @returns {Object} configObj
        */
        const getConfigDetails = (recordId) => {
            try {
                let configObj = {};
                let customrecord_jj_fedex_api_detailsSearchObj = search.create({
                    type: "customrecord_jj_fedex_api_details",
                    filters: [
                        ["internalid", "anyof", recordId]
                    ],
                    columns: [
                        search.createColumn({ name: "custrecord_jj_client_id", label: "Client Id" }),
                        search.createColumn({ name: "custrecord_jj_client_secret", label: " Client Secret" }),
                        search.createColumn({ name: "custrecord_jj_api_endpoint_url", label: "API Endpoint URL" })
                    ]
                });
                let searchResultCount = customrecord_jj_fedex_api_detailsSearchObj.runPaged().count;
                log.debug("customrecord_jj_fedex_api_detailsSearchObj result count", searchResultCount);
                if (searchResultCount > 0) {
                    customrecord_jj_fedex_api_detailsSearchObj.run().each(function (result) {
                        configObj.client_id = result.getValue({ name: "custrecord_jj_client_id", label: "Client Id" });
                        configObj.client_secret = result.getValue({ name: "custrecord_jj_client_secret", label: " Client Secret" });
                        configObj.posturl = result.getValue({ name: "custrecord_jj_api_endpoint_url", label: "API Endpoint URL" });
                        return true;
                    });
                    log.debug("Config Details", configObj);
                    return configObj;
                } else {
                    return configObj;
                }
            } catch (e) {
                log.error("error@getConfigDetails", e);
                return {};
            }
        };

        /**
         * @description Get the access token of the FedEx and UPS API based on configuration details. 
         * @param {Object} configDetails 
         * @param {string} requestType - Type of request to differentiate API requests.
         * @returns {Object} accessToken
         */
        const getAccessToken = (configDetails, requestType) => {
            try {
                let body;
                let headersValue;
                let responseAccessToken;

                if (requestType === 'FedEx') {
                    log.debug("FedEx***")
                    body = {
                        'grant_type': 'client_credentials',
                        'client_id': configDetails.client_id,
                        'client_secret': configDetails.client_secret
                    };
                    headersValue = {
                        'Accept': 'application/json',
                        'Content-Type': 'application/x-www-form-urlencoded'
                    };
                    responseAccessToken = https.post({
                        url: configDetails.posturl,
                        headers: headersValue,
                        body: body
                    });
                    log.debug("Access Token Response FedEx", responseAccessToken);

                } //grant_type=authorization_code&code=string&redirect_uri=string&code_verifier=string 
                else if (requestType === 'UPS') {
                    log.debug("UPS***")
                    body = {
                        'grant_type': 'client_credentials',
                        'code': '25M2kKG1',
                        'redirect_uri': 'https://test.com'
                    };

                    // Create the base64-encoded authorization header
                    let encodedCredentials = encode.convert({
                        string: configDetails.client_id + ':' + configDetails.client_secret,
                        inputEncoding: encode.Encoding.UTF_8,
                        outputEncoding: encode.Encoding.BASE_64
                    });
                    log.debug("encodedCredentials", encodedCredentials)
                    headersValue = {
                        'Content-Transfer-Encoding': 'application/x-www-form-urlencoded',
                        'Authorization': 'Basic ' + encodedCredentials
                    };
                    responseAccessToken = https.post({
                        url: configDetails.posturl,
                        headers: headersValue,
                        body: body
                    });
                    log.debug("Access Token Response UPS", responseAccessToken);
                }

                let responseBody = JSON.parse(responseAccessToken.body);
                log.debug("Parsed Access Token Response", responseBody);

                if (Object.keys(responseBody).length > 0) {
                    return responseBody;
                } else {
                    return {};
                }
            } catch (e) {
                log.error("error@getAccessToken", e);
                return {};
            }
        };

        /**
         * Defines the function that is executed at the beginning of the map/reduce process and generates the input data.
         * @param {Object} inputContext
         * @returns {Array} The input data to use in the map/reduce process
         * @since 2015.2
         */
        const getInputData = (inputContext) => {
            try {
                log.debug("enter get input")
                let configDetails1 = getConfigDetails(1);
                log.debug("configDetails1", configDetails1)
                let configDetails2 = getConfigDetails(2);
                log.debug("configDetails2", configDetails2)

                let accessToken1 = getAccessToken(configDetails1, 'FedEx');
                let accessToken2 = getAccessToken(configDetails2, 'UPS');

                log.debug("Access Token 1", accessToken1);
                log.debug("Access Token 2", accessToken2);
                log.debug("Access Token 11", accessToken1.access_token);
                log.debug("Access Token 22", accessToken2.access_token);

                return [
                    { recordId: 1, token: accessToken1.access_token },
                    { recordId: 2, token: accessToken2.access_token }
                ];
            } catch (e) {
                log.error("error@getInputData", e);
            }
        };

        /**
         * Defines the function that is executed when the reduce entry point is triggered.
         * @param {Object} reduceContext
         * @since 2015.2
         */
        const reduce = (reduceContext) => {
            try {
                log.debug("enter reduce")
                let values = JSON.parse(reduceContext.values[0]);

                log.debug("Reduce Values", values);

                record.submitFields({
                    type: 'customrecord_jj_fedex_api_details',
                    id: values.recordId,
                    values: {
                        custrecord_jj_access_token: values.token || ''
                    },
                    options: {
                        enableSourcing: true,
                        ignoreMandatoryFields: true
                    }
                });

            } catch (e) {
                log.error("error@reduce", e);
            }
        };

        /**
         * Defines the function that is executed when the summarize entry point is triggered.
         * @param {Object} summaryContext
         * @since 2015.2
         */
        const summarize = (summaryContext) => {
            log.audit("Summary", {
                concurrency: summaryContext.concurrency,
                dateCreated: summaryContext.dateCreated,
                isRestarted: summaryContext.isRestarted,
                seconds: summaryContext.seconds,
                usage: summaryContext.usage,
                yields: summaryContext.yields
            });

            if (summaryContext.inputSummary.error) {
                log.error("Input Summary Error", summaryContext.inputSummary.error);
            }
            if (summaryContext.mapSummary.error) {
                log.error("Map Summary Error", summaryContext.mapSummary.error);
            }
            if (summaryContext.reduceSummary.error) {
                log.error("Reduce Summary Error", summaryContext.reduceSummary.error);
            }
        };

        return { getInputData, reduce, summarize };

    });

Leave a comment

Your email address will not be published. Required fields are marked *