Search code examples
arraysgoogle-sheetsgoogle-apps-scriptmultidimensional-array

Google Script Array within an Array not doing as I expect


I'm collecting an array of data within one for loop of my code. In a second for loop (looking at a different data source) I want to add an array of users google accounts.

The 'instrumentGroups[]' array should have these elements: {FolderName, FolderID, FolderViewers and NewViewers[]}. The FolderViewers is correctly created as an array by the getViewers() function. I want to be able to add the NewViewers in the second loop.

I thought I'd cracked it with the code below, but whenever the .push occurs in the second loop it updates all the 'NewViewers' arrays in the 'InstrumentGroups' array. Presumably there is really only one 'NewViewers' array. How do I ensure there is a 'NewViewers' array for each entry in the 'InstrumentGroups'. A simplified version of the code is here:

var fldrViewers, newViewer=[];
var instrumentGroups=[], userGoogleAccount;

for (nCounter=0; childFolders.hasNext(); nCounter++){ //on exit from this loop, instrumentGroups has the list of folders, their ID and viewers emails.
    //explore how to identify a folder within a drive
    childFolder=childFolders.next();
    childFolderName=childFolder.getName();
    childFolderID=childFolder.getId();
    fldrViewers=childFolder.getViewers().map((user) => user.getEmail());
    instrumentGroups.push({FolderName : childFolderName, FolderID : childFolderID, FolderViewers : fldrViewers, NewViewers : newViewer});
  }

for (userCounter=1; userCounter<=rRows; userCounter++){
    for (nCounter=0; nCounter<instrumentGroups.length; nCounter++) { //find the entry in instrumentGroups that contains the instrument of the player.
      if (rRange.getCell(userCounter, FOLDER_COL).getValue()==instrumentGroups[nCounter].FolderName){
        userGoogleAccount=rRange.getCell(userCounter,GOOGLE_ACCOUNT_COL).getValue();
        instrumentGroups[nCounter].NewViewers.push(userGoogleAccount);
        break;
      }
    }
  }

Even after the first iteration every entry in InstrumentGroups will have the user's Google Account populated. Perhaps the answer is to add the new users array only in the second loop, but I've no idea how to achieve that - it needs to be an array as the number of new users in each group varies.

I suspect this is something simple, but its escaped my attempts to solve it. I hope the explanation above is sufficiently clear.

Grateful for any help.

Regards


Solution

  • I've discovered the problem:

    This declaration: var newViewer=[]; creates a blank array.
    This code: instrumentGroups.push({FolderName : childFolderName, ....., NewViewers : newViewer}); creates a reference to the newViewer array as an item named NewViewers. Each entry in the instrumentsGroup has the same reference and hence the .push statement updates every entry.

    The answer was to change to this: instrumentGroups.push({FolderName : childFolderName, ....., NewViewers : new Array()}); which creates a new reference for each entry and the subsequent .push statement adds the information to the correct array only.