A little bit of Javascript help with pnp

Hiya Plumsail!

I have this code with 2 functions in it (there are more but these 2 are the only ones I am having trouble with):
var invoiceLineItemsHMTL ='';
var invoiceLineItems = pnp.sp.web.getList('/sites/COREaaS-OrderSystem/Lists/Order Line Items').items;

function parseLineItemData(lineItemData){
    console.log(lineItemData);   
    for (i=0; i<lineItemData.length; i++){
            invoiceLineItemsHMTL += lineItemData[i].Beginning_x0020_HTML_x0020_Code_ + lineItemData[i].Ending_x0020_HTML_x0020_Code_x00 
            + lineItemData[i].Ending_x0020_HTML_x0020_Code_x00;
        }
    console.log('returning invoicelinehtml');
    console.log(invoiceLineItemsHMTL);
    return invoiceLineItemsHMTL
}
   
//function to grab line item information and parse it
function getLineItemData(list,Id){
    //Get Line Item Data
    list.filter('Invoice_x0020_No_x002e_/ID eq ' + Id)
    .select('Beginning_x0020_HTML_x0020_Code_','Middle_x0020_HTML_x0020_Code_x00','Ending_x0020_HTML_x0020_Code_x00').get()
    .then(lineItemData => {parseLineItemData(lineItemData)});
}

getLineItemData(invoiceLineItems,28);

I am not sure what I am doing wrong, but what is returned by the function is "undefined", but the console.logs log the expected information to the console. How can get the function to return the desired information like console.log does!

Note; Whether I have the invoiceLineItemHTML inside or outside the parseLineItemData function doesn't make a difference. :frowning:

Also, if I manually call the function with the array from lineItemData manually, it returns the correct string, it is just when it is called within the getLineItemData function, that the correct string is not returned...

Thanking you in advance!

Hello @Jamal_Smith-Graham,

What exactly are you doing with this code? Could you please describe a use case.

Where do you run this code? Under what event?

Hiya @mnikitina

This code is executed on the press of a button on a form to create an invoice. There is a related List control that contains all the invoice line items, and what I am doing is getting all the relevant HTML from those list items (Beginning_x0020_HTML_x0020_Code_','Middle_x0020_HTML_x0020_Code_x00','Ending_x0020_HTML_x0020_Code_x00') and concat them (that is the for loop) and then return the line item data in HTML form to a function that will then do a fetch call to create the PDF.

Everything works except this part of the parseLineItemData that returns undefined instead of the all the HTML from all the Line items in the related field. But if I check invoiceLineItems in the console, it shows the correct content.

Hello @Jamal_Smith-Graham,

Are you getting any errors in browser console(F12) when running the code on button click?

Is the item ID hardcoded or is it passed dynamically?

Hiya @mnikitina

It is dynamically passed, it does work as console.log(invoiceLineItemsHMTL) returns the correct text, there are no errors in the console. It is just that return invoiceLineItemsHTML returns "undefined", it is as if invoiceLineItemsHTML is returned before the calculation is done.

Hello @Jamal_Smith-Graham,

Please test the code below. Please add only this code to the button's Click property.

Are you getting the same result?


    var invoiceLineItems = pnp.sp.web.getList('/sites/COREaaS-OrderSystem/Lists/Order Line Items').items;

    //function to grab line item information and parse it
    function getLineItemData(list,Id){
        //Get Line Item Data
        list.filter('Invoice_x0020_No_x002e_/ID eq ' + Id)
        .select('Beginning_x0020_HTML_x0020_Code_','Middle_x0020_HTML_x0020_Code_x00','Ending_x0020_HTML_x0020_Code_x00').get()
        .then(function(lineItemData){
            var invoiceLineItemsHMTL =''; 
            console.log(lineItemData);   
            for (i=0; i<lineItemData.length; i++){
                invoiceLineItemsHMTL += lineItemData[i].Beginning_x0020_HTML_x0020_Code_ + lineItemData[i].Ending_x0020_HTML_x0020_Code_x00 
                + lineItemData[i].Ending_x0020_HTML_x0020_Code_x00;
            }
            console.log('returning invoicelinehtml');
            console.log(invoiceLineItemsHMTL);
            return invoiceLineItemsHMTL                    
        });
    }

    getLineItemData(invoiceLineItems,28);

Hiya @mnikitina

This is what I get when pressing the button in the console:

This is what I get when running the code in the console:

It is returning the result before the for loop is finished it seems! I am so confused!

@Jamal_Smith-Graham,

The HTML code is the same in both cases. Is it the correct one?

Hiya @mnikitina

I figured it out in the end, this is what the code needed to be, we needed a return on the filter, not sure if we need the second return... probably not! lol. Thanks for your help anyway :slight_smile: :

//function to grab line item information and parse it
const getLineItemData = function(list,Id) {
    var invoiceLineItemsHTML = "";
    //Get Line Item Data
    return list.filter('Invoice_x0020_No_x002e_/ID eq ' + Id)
        .select('Beginning_x0020_HTML_x0020_Code_','Middle_x0020_HTML_x0020_Code_x00','Ending_x0020_HTML_x0020_Code_x00').get()
        .then(function(lineItemData){
            for (i=0; i<lineItemData.length; i++){
                invoiceLineItemsHTML += lineItemData[i].Beginning_x0020_HTML_x0020_Code_ + lineItemData[i].Middle_x0020_HTML_x0020_Code_x00 
                + lineItemData[i].Ending_x0020_HTML_x0020_Code_x00;   
            }
            return invoiceLineItemsHTML;
        });
}
1 Like