Search code examples
searchnetsuitesuitescriptsuitescript2.0

Trying to Set a Custom Field Value on a Customer, from a Custom Record Field


I'm struggling with a script that is supposed to:

  1. Search for a list of Customer's
  2. Get a couple of Field Values, one of which is used in the next Search, the other is the ID
  3. Search for a list of Custom Records, the criteria being one of the fields I just fetched
  4. Get a field value
  5. And use the Customer ID fetched earlier to assign the Custom Record field value to a Custom field on the Customer.

But it is dropping out on the second search, saying that it is returning "undefined" due to invalid Search Criteria. I'm assuming that the field I get from the first search is not working in the Criteria of the second search?

My code is below - is it an obvious one (as usual), or is it literally the wrong way to go about this?

/**
 *@NApiVersion 2.x
 *@NScriptType ScheduledScript
 */

define(['N/search'],

function getShipSuburbId(search) {
  function execute() {
    var customerSearchObj = search.create({
        type: "customer",
        filters:
            [
                ["custentity_store_shipping_suburb","isnotempty",""]
            ],
        columns:
            [
                search.createColumn({
                    name: "entityid"
                }),
                search.createColumn({name: "custentity_store_shipping_suburb"})
            ]
    });
    var custSearchResult = customerSearchObj.runPaged({pageSize: 1000});
    log.debug({title: "customerSearchObj result count", details: custSearchResult.count});
    var custNumPages = custSearchResult.pageRanges.length;
    var custAllResults = [];
    var i = 0;
    while (i < custNumPages) {
        custAllResults = custAllResults.concat(custSearchResult.fetch(i).data);
        i++;
    }

        return custAllResults;
        for (var j = 0; j < custAllResults.length; j++) {
            var currentRecord = custAllResults[j].getValue({
                name: "entityid"
            });
            var shipSub = custAllResults[j].getValue({
                name: "custentity_store_shipping_suburb"
            });
};

var shipSubIdSearch = search.create({
   type: "customrecord_suburb",
   filters:
   [
      ["name","is",shipSub]
   ],
   columns:
   [
      search.createColumn({
         name: "internalid",
         summary: "MAX",
         label: "Internal ID"
      })
   ]
});

        var allSubIdResults = shipSubIdSearch.runPaged({pageSize: 1});
    log.debug({title: "shipSubIdSearch result count", details: allSubIdResults.count});
    var subNumPages = custSearchResult.pageRanges.length;
    var subAllResults = [];
    var m = 0;
    while (m < subNumPages) {
        subAllResults = subAllResults.concat(allSubIdResults.fetch(m).data);
        m++;
    }
          return subAllResults;
          
    for (var k = 0; k < subAllResults.length; k++) {
    var shipSubId = subAllResults[k].getValue({
        name: "internalid"
    });
};
      var setSuburbId = currentRecord.setValue({

                    fieldId: 'custentity_shipping_suburb_id',

                    value: shipSubId

                });
      return setSuburbId;
  }
  return {
    execute : execute
  };

});

NEW CODE BELOW

/**
 *@NApiVersion 2.x
 *@NScriptType ScheduledScript
 */

define(['N/search', 'N/record'],

function getShipSuburbId(search, record) {
  function execute() {

      var customerSearchObj = search.create({
          type: "customer",
          filters:
              [
                  ["custentity_store_shipping_suburb", "isnotempty", ""]
              ],
          columns:
              [
                  search.createColumn({
                      name: "entityid"
                  }),
                  search.createColumn({name: "custentity_store_shipping_suburb"})
              ]
      });     // The first search, which draws a list of Customers

      var custSearchResult = customerSearchObj.runPaged({pageSize: 1000});    // Run paged
      log.debug({title: "customerSearchObj result count", details: custSearchResult.count});
      var custNumPages = custSearchResult.pageRanges.length;

      var custAllResults = [];
      var i = 0;
      while (i < custNumPages) {
          custAllResults = custAllResults.concat(custSearchResult.fetch(i).data);
          i++;
      }

      for (var j = 0; j < custAllResults.length; j++) {
          var currentRecord = custAllResults[j].getValue({
              name: "entityid"
          });
          var shipSub = custAllResults[j].getValue({
              name: "custentity_store_shipping_suburb"
          });
          log.debug({title: "currentRecord", details: currentRecord});
          log.debug({title: "shipSub", details: shipSub});
          // I've left this "for" operation open for the next search - possible issue?


          var shipSubIdSearch = search.create({
              type: "customrecord_suburb",
              filters:
                  [
                      ["name", "is", shipSub]
                  ],
              columns:
                  [
                      search.createColumn({
                          name: "internalid",
                          summary: "MAX",
                          label: "Internal ID"
                      })
                  ]
          }); // Second search. This should only return one result each time it is run
          var subIdRun = shipSubIdSearch.run();
          log.debug({title: "subIdRun result count", details: subIdRun.count});

          var shipSubId = subIdRun.each(
            function (result) {
              log.debug({
                  title: "Fetch ID",
                  details: result.getValue({name: "internalid"})
              })
              return true;
          });
          log.debug({title: "shipSubId result", details: shipSubId});

          var myRecord = record.load({
              type: 'customer',
              id: currentRecord
          }); // Load the Customer record, based on the id fetched in the first search
          log.debug({title: "myRecord", details: myRecord});

          myRecord.setValue({

              fieldId: 'custentity_shipping_suburb_id',

              value: shipSubId

          }); // And set the value of the Custom field, based on value from second search

      }
  }
  return {
    execute : execute
  };

});

And screenshot of Execution Log on New Script: Screenshot of Execution Log


Solution

  • I have found the best way to approach multiple levels of searching, is to gather the results of each search into an array.
    Once I have finished dealing with the results of one search, then process each element of the array one by one, whether that be searching, querying, editing, etc.

    The advantages of this include:

    1. If a scheduled script, this allows me to check the governance usage after the first search, and reschedule with the array of results as a parameter if necessary.
    2. Handling other logic like sorting or formulas on the array elements, before continuing with other operations.
    3. Potentially faster processing, particularly if you don't need to process any further operations on some results of the first search.
    4. This is just personal preference, but it makes it easier to split elements of the script into separate functions and maintain readability and logical sequence.