Skip to content

Commit

Permalink
fix updates
Browse files Browse the repository at this point in the history
  • Loading branch information
CherrelleTucker committed Jan 17, 2024
1 parent f12b8e0 commit 98fc965
Showing 1 changed file with 8 additions and 232 deletions.
240 changes: 8 additions & 232 deletions actionTrackerSheet.js
Original file line number Diff line number Diff line change
@@ -1,21 +1,13 @@
/* Purpose:
1. Search agendas for action items to be completed and populate in the Action Tracking Google Sheet.
2. Push status updates from from the Action Tracking Google sheet to the Action source agendas as changed.
/* Purpose:
1. Search agendas for action items to be completed and populate in the Action Tracking Google Sheet.
2. Push status updates from from the Action Tracking Google sheet to the Action source agendas as changed.
Future development:
Preserve links in task items from the source documents. Will first require the same development in the inDocActionItems script, as the links are lost in that action first.
Future development:
Preserve links in task items from the source documents. Will first require the same development in the inDocActionItems script, as the links are lost in that action first.
To note:
This script is developed as a Google Apps Script container script: i.e. a script that is bound to a specific file, such as a Google Sheets, Google Docs, or Google Forms file. This container script acts as the file's custom script, allowing users to extend the functionality of the file by adding custom functions, triggers, and menu items to enhance its behavior and automation.
To note:
This script is developed as a Google Apps Script container script: i.e. a script that is bound to a specific file, such as a Google Sheets, Google Docs, or Google Forms file. This container script acts as the file's custom script, allowing users to extend the functionality of the file by adding custom functions, triggers, and menu items to enhance its behavior and automation.
<<<<<<< HEAD
Instructions for Using this Script in your container file:
1. Open a new or existing Google Sheets file where you want to use the script.
2. Click on "Extensions" in the top menu and select "Apps Script" from the dropdown menu. This will open the Google Apps Script editor in a new tab.
Expand All @@ -36,28 +28,6 @@ Note: Make sure to properly set up the correct folder structure in Google Drive
function getSpreadsheetInfoTest() {
// Get the active spreadsheet
var spreadsheet = SpreadsheetApp.getActiveSpreadsheet();
=======
// Instructions for Using this Script in your container file:
// 1. Open a new or existing Google Sheets file where you want to use the script.
// 2. Click on "Extensions" in the top menu and select "Apps Script" from the dropdown menu. This will open the Google Apps Script editor in a new tab.
// 3. Copy and paste the provided script into the Apps Script editor, replacing the existing code (if any).
// 4. In the MOPopulate function, replace the placeholder values for folderId and spreadsheetId with the actual IDs of your Google Drive folder containing the agendas and the Google Sheets spreadsheet where you want to track the actions, respectively.
// 5. In the updateStatus function, replace the placeholder value for spreadsheetId with the actual ID of your Google Sheets spreadsheet.
// 6. Save the script by clicking on the floppy disk icon or by pressing "Ctrl + S" (Windows) or "Cmd + S" (Mac).
// 7. Go back to your Google Sheets file, refresh the page, and you'll see a new custom menu labeled "Action Items" in the top menu.
// 8. Click on "Action Items" in the top menu to access the custom menu. You'll find two options:
// a. "Get Actions from Agendas": This option will pull actions from the specified agendas and populate them in the "MO" sheet in your Google Sheets file.
// b. "Update Status in Source Document": This option will push status updates from the "MO" sheet back to the corresponding action items in the source agendas.
// 9. Whenever you want to get actions from the agendas or update status in the source documents, simply click on the corresponding option from the "Action Items" menu.
// Note: Make sure to properly set up the correct folder structure in Google Drive and name your agendas and sheets according to the script's logic for pulling and updating actions. This documentation assumes you have some basic familiarity with Google Apps Script and how to run container-bound scripts within a Google Sheets file.

//////////////////////////////////////////////////

// Global Variables: Replace 'folderId' and 'spreadsheetId' with your actual Google Drive folder ID and Google Sheets spreadsheet ID, respectively.
// var folderId = '1WKYw4jnP6ejRkOLAIPoPvbEYClaLE4eR'; // SNWG MO Weekly Internal Planning > FY 23 Google Drive folder
var folderId = '1SRIUs7CUEdGUw0r1PI52e0OJpfXYN0z8'; // SNWG MO Weekly Internal Planning > FY 24 Google Drive folder
var spreadsheetId = '1uYgX660tpizNbIy44ddQogrRphfwZqn1D0Oa2RlSYKg'; // SNWG MO Action Tracking Spreadsheet
>>>>>>> b746d3712728e7b81086aac526d2a6c48e28b83d

// Get the spreadsheet name
var spreadsheetName = spreadsheet.getName();
Expand Down Expand Up @@ -95,24 +65,18 @@ function logExecutionTime(func, functionName) {

// Add a custom menu to the spreadsheet
function onOpen() {
<<<<<<< HEAD
var ui = SpreadsheetApp.getUi();
ui.createMenu('Action Items')
.addItem('Pull actions for ALL folders', 'pullActionsForAllFolders')
.addItem('Pull actions for MO', 'pullActionsForFolderMO')
.addItem('Pull actions for SEP', 'pullActionsForFolderSEP')
.addItem('Pull actions for DevSeed', 'pullActionsForFolderDevSeed')
.addItem('Pull actions for Assessment HQ', 'pullActionsForFolderAssessmentHQ')
.addSeparator()
.addItem('Push actions from ALL tabs', 'pushActionsFromAllTabs')
.addItem('Push actions from MO', 'pushActionsFromTabMO')
.addItem('Push actions from SEP', 'pushActionsFromTabSEP')
.addItem('Push actions from DevSeed', 'pushActionsFromTabDevSeed')
=======
SpreadsheetApp.getUi()
.createMenu('Action Items')
.addItem('Get Actions from Agendas','MOPopulate')
.addItem('Push Status Updates to Source Document','updateStatus')
>>>>>>> b746d3712728e7b81086aac526d2a6c48e28b83d
.addToUi();
}

Expand All @@ -121,7 +85,8 @@ var spreadsheetId = '13xgmbfP8X8lu9tlD_cHVCF9RmQeKvToqtbiDSfp_Nfg'; // Testing A
var folderIds = {
MO: '1SRIUs7CUEdGUw0r1PI52e0OJpfXYN0z8',
SEP: '1Cw_sdH_IleGbtW1mVoWnJ0yqoyzr4Oe0',
DevSeed: '1Bvj1b1u2LGwjW5fStQaLRpZX5pmtjHSj'
DevSeed: '1Bvj1b1u2LGwjW5fStQaLRpZX5pmtjHSj',
AssessmentHQ: '1MEKTRBKum3UA4q97i9FJeBn49tMckbIn'// Assessment HQ Weekly Agenda/Notes
};

///////////////////Pull///////////////////////////////////////////////
Expand Down Expand Up @@ -156,58 +121,11 @@ function pullActionsForFolderDevSeed() {
}, 'pullActionsForFolderDevSeed');
}

// Helper function to pull actions from a specific folder
function pullActionsForFolder(folderName) {
var folderId = folderIds[folderName];
var tablePullSheetName = folderName;

Logger.log('Step 1: Pulling actions from documents...');
var actions = pullActionsFromDocuments(folderId);
Logger.log('Step 1: Actions retrieved:', actions);

Logger.log('Step 2: Populating sheet with actions...');
populateSheetWithActions(spreadsheetId, tablePullSheetName, actions);
Logger.log('Step 2: Sheet populated with actions.');
}

// Global variables
var spreadsheetId = '13xgmbfP8X8lu9tlD_cHVCF9RmQeKvToqtbiDSfp_Nfg'; // Testing ALL Action Tracking Sheet
var folderIds = {
MO: '1SRIUs7CUEdGUw0r1PI52e0OJpfXYN0z8',
SEP: '1Cw_sdH_IleGbtW1mVoWnJ0yqoyzr4Oe0',
DevSeed: '1Bvj1b1u2LGwjW5fStQaLRpZX5pmtjHSj'
};

///////////////////Pull///////////////////////////////////////////////

// Function to pull actions for all folders
function pullActionsForAllFolders() {
logExecutionTime(function() {
pullActionsForFolder('MO');
pullActionsForFolder('SEP');
pullActionsForFolder('DevSeed');
}, 'pullActionsForAllFolders');
}

// Function to pull actions for MO folder
function pullActionsForFolderMO() {
logExecutionTime(function() {
pullActionsForFolder('MO');
}, 'pullActionsForFolderMO');
}

// Function to pull actions for SEP folder
function pullActionsForFolderSEP() {
// Function to pull actions for AssessmentHQ folder
function pullActionsForFolderAssessmentHQ() {
logExecutionTime(function() {
pullActionsForFolder('SEP');
}, 'pullActionsForFolderSEP');
}

// Function to pull actions for DevSeed folder
function pullActionsForFolderDevSeed() {
logExecutionTime(function() {
pullActionsForFolder('DevSeed');
}, 'pullActionsForFolderDevSeed');
pullActionsForFolder('AssessmentHQ');
}, 'pullActionsForFolderAssessmentHQ');
}

// Helper function to pull actions from a specific folder
Expand Down Expand Up @@ -272,7 +190,6 @@ function pullActionsFromDocuments(folderId) {
return allActions;
}

// Pull helper function: Find the second table with qualifying headers
// Pull helper function: Find the second table with qualifying headers
function findSecondTable(tables) {
for (var i = 0; i < tables.length; i++) {
Expand All @@ -295,7 +212,6 @@ function findSecondTable(tables) {
return null;
}

// Pull helper function: Convert table to 2D array for convenience and flexibility in data processing
// Pull helper function: Convert table to 2D array for convenience and flexibility in data processing
function tableTo2DArray(table) {
var numRows = table.getNumRows();
Expand All @@ -314,7 +230,6 @@ function tableTo2DArray(table) {
return data;
}

// Pull helper function: Populate the Sheet with actions
// Pull helper function: Populate the Sheet with actions
function populateSheetWithActions(spreadsheetId, sheetName, actions) {
var spreadsheet = SpreadsheetApp.openById(spreadsheetId);
Expand All @@ -325,8 +240,6 @@ function populateSheetWithActions(spreadsheetId, sheetName, actions) {
} else {
// Clear only the contents of columns A to E
sheet.getRange(1, 1, sheet.getMaxRows(), 5).clearContent();
// Clear only the contents of columns A to E
sheet.getRange(1, 1, sheet.getMaxRows(), 5).clearContent();
}

var headerRow = ['Action Source', 'Status', 'Assigned to', 'Task'];
Expand All @@ -336,24 +249,18 @@ function populateSheetWithActions(spreadsheetId, sheetName, actions) {
var numCols = headerRow.length;

if (numRows > 0 && numCols > 0) {
// Set values starting from cell A1
// Set values starting from cell A1
var range = sheet.getRange(1, 1, numRows, numCols);
range.setValues(actions);
}
}

<<<<<<< HEAD
// Primary Pull function: Pull action items from meeting notes to populate action tracking workbook
=======
// Primary function: Pull action items from meeting notes to populate action tracking workbook
>>>>>>> b746d3712728e7b81086aac526d2a6c48e28b83d
function MOPopulate() {
var tablePullSheetName = 'MO';

Logger.log('Step 1: Pulling actions from documents...');
var actions = pullActionsFromDocuments(folderIds.MO);
var actions = pullActionsFromDocuments(folderIds.MO);
Logger.log('Step 1: Actions retrieved:', actions);

Logger.log('Step 2: Populating sheet with actions...');
Expand All @@ -370,16 +277,6 @@ pullActionsForFolderDevSeed: success 10:59:36 AM pullActionsForFolderDevSeed e
pullActionsForAllFolders: success 11:02:56 AM pullActionsForAllFolders execution time: 0 minutes, 37.867 seconds
*/

////////////////// Push ////////////////////////////////////////////////////////
////////////////// Pull Testing Log //////////////////////////////////////////

/*
pullActionsForFolderMO: success 2024-01-11 10:43:24 AM pullActionsForFolderMO execution time: 0 minutes, 12.737 seconds
pullActionsForFolderSEP: success 2024-01-10 10:46:01 AM pullActionsForFolderSEP execution time: 0 minutes, 10.042 seconds
pullActionsForFolderDevSeed: success 10:59:36 AM pullActionsForFolderDevSeed execution time: 0 minutes, 9.670 seconds
pullActionsForAllFolders: success 11:02:56 AM pullActionsForAllFolders execution time: 0 minutes, 37.867 seconds
*/

////////////////// Push ////////////////////////////////////////////////////////

// Function to call the primary function on all named tabs
Expand Down Expand Up @@ -481,108 +378,8 @@ function findTableByHeadings(body, headings) {
return headerRow.getText().indexOf(heading) !== -1;
})) {
return table;
// Function to call the primary function on all named tabs
function pushActionsFromAllTabs() {
logExecutionTime(function() {
updateStatusOnTab("MO");
updateStatusOnTab("SEP");
updateStatusOnTab("DevSeed");
}, 'pushActionsFromAllTabs');
}

// Function to call the primary function on the "MO" tab
function pushActionsFromTabMO() {
logExecutionTime(function() {
updateStatusOnTab("MO");
}, 'pushActionsFromTabMO');
}

// Function to call the primary function on the "SEP" tab
function pushActionsFromTabSEP() {
logExecutionTime(function() {
updateStatusOnTab("SEP");
}, 'pushActionsFromTabSEP');
}

// Function to call the primary function on the "DevSeed" tab
function pushActionsFromTabDevSeed() {
logExecutionTime(function() {
updateStatusOnTab("DevSeed");
}, 'pushActionsFromTabDevSeed');
}

function updateStatusOnTab(tabName) {
var sheet = SpreadsheetApp.getActiveSpreadsheet().getSheetByName(tabName);
var range = sheet.getRange("A:G"); // Assuming the URL is in Column G
var values = range.getValues();

// Loop through each row of the data
for (var i = 1; i < values.length; i++) {
var actionSourceUrl = values[i][6]; // Column G (assuming the URL is in Column G)
var status = values[i][1]; // Column B
var assignedTo = values[i][2]; // Column C
var task = values[i][3]; // Column D

// Check if the row is empty or if it's the header row
if (actionSourceUrl || status || assignedTo || task) {
// Log actionSourceUrl for investigation
console.log("Row:", i + 1, "actionSourceUrl:", actionSourceUrl);

// Call the function to update status in the source document
updateStatusInSourceDoc(actionSourceUrl, status, task);
}
}
}

function updateStatusInSourceDoc(actionSource, status, task) {
// Column G now contains the extracted URL
var actionSourceUrl = actionSource; // No need for extractUrlFromHyperlink

if (!actionSourceUrl) {
console.error("Invalid URL in Column A:", actionSource);
return;
}

try {
console.log("Attempting to open document with URL:", actionSourceUrl);
var sourceDoc = DocumentApp.openByUrl(actionSourceUrl);
} catch (error) {
console.error("Error opening document by URL:", error);
return;
}
// Get the body of the document
var body = sourceDoc.getBody();

// Find the table with the specified headings
var table = findTableByHeadings(body, ["Status", "Action"]);

if (table) {
// Find the row with the matching task in the "Action" column
var rowIndex = findRowIndexByColumnValue(table, "Action", task);

if (rowIndex !== -1) {
// Update the "Status" column with the status from the sheet
table.getCell(rowIndex, getColumnIndex(table, "Status")).setText(status);
}
}
}

function findTableByHeadings(body, headings) {
// Function to find a table in the document with specified headings
var tables = body.getTables();

for (var i = 0; i < tables.length; i++) {
var table = tables[i];
var headerRow = table.getRow(0);

// Check if the table has the specified headings
if (headings.every(function (heading) {
return headerRow.getText().indexOf(heading) !== -1;
})) {
return table;
}
}


return null;
}
Expand Down Expand Up @@ -618,13 +415,7 @@ function getColumnIndex(table, columnName) {
return -1;
}

<<<<<<< HEAD
////////////////// Push Testing Log //////////////////////////////////////////
=======
// Primary function: push status updates back to action tracking tables in meeting notes
function updateStatus() {
var sheetName = 'MO'; // <--Replace with the name of your sheet
>>>>>>> b746d3712728e7b81086aac526d2a6c48e28b83d

/*
'pushActionsFromTabMO': success 3:59:02 PM execution time: 0 minutes, 13.421 seconds
Expand All @@ -633,17 +424,8 @@ function updateStatus() {
'pushActionsFromAllTabs': 4:16:43 PM execution time: 0 minutes, 31.064 seconds
*/

<<<<<<< HEAD
///////////////Combine Open Actions///////////////////////////////////////////////

=======
Logger.log('Step 2: Syncing status to source documents...');
syncStatusToSource(actions);
Logger.log('Step 2: Status synced to source documents.');
}

//////////////////////////////////////////////////////////////
>>>>>>> b746d3712728e7b81086aac526d2a6c48e28b83d
// function to copy all rows of each sheet that do not contain "Done" in the "Status Column". Maintain column D formatting from source sheet to track length of time the action has been open.
function copyDataToAllOpenSheet() {
// Get a reference to the currently open spreadsheet
Expand Down Expand Up @@ -697,10 +479,4 @@ function copyDataToAllOpenSheet() {
targetRange.setFontWeights([[fonts[rowIndex][3]]]);
}
});
<<<<<<< HEAD
}
=======
}


>>>>>>> b746d3712728e7b81086aac526d2a6c48e28b83d
}

0 comments on commit 98fc965

Please sign in to comment.