Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Writing an 'Undo' Function for Google Spreadsheets Using GAS

Currently there is no undo() function for Google Apps Script in the Spreadsheet/Sheet/Range classes. There were a few issues opened on the Issue Tracker, I can only find one now (I don't know what Triaged means): here.

There have been suggested workarounds using the DriveApp and revision history but I took a look around and didn't find anything (maybe it's buried?). In any case, an undo() function is incredibly necessary for so many different operations. I could only think of one kind of workaround, but I haven't been able to get it to work (the way the data is stored, I don't know if it's even possible). Here is some pseudo -

function onOpen () {
  // Get all values in the sheet(s)
  // Stringify this/each (matrix) using JSON.stringify
  // Store this/each stringified value as a Script or User property (character limits, ignore for now)
}

function onEdit () {
  // Get value of edited cell
  // Compare to some value (restriction, desired value, etc.)
  // If value is not what you want/expected, then:
  // -----> get the stringified value and parse it back into an object (matrix)
  // -----> get the old data of the current cell location (column, row)
  // -----> replace current cell value with the old data
  // -----> notifications, coloring cell, etc, whatever else you want
  // If the value IS what you expected, then:
  // -----> update the 'undoData' by getting all values and re-stringifying them
  //        and storing them as a new Script/User property
}

Basically, when the Spreadsheet is opened store all values as a Script/User property, and only reference them when certain cell criteria(on) are met. When you want to undo, get the old data that was stored at the current cell location, and replace the current cell's value with the old data. If the value doesn't need to be undone, then update the stored data to reflect changes made to the Spreadsheet.

So far my code has been a bust, and I think it's because the nested array structure is lost when the object is stringified and stored (e.g., it doesn't parse correctly). If anyone has written this kind of function, please share. Otherwise, suggestions for how to write this will be helpful.

Edit: These documents are incredibly static. The number of rows/columns will not change, nor will the location of the data. Implementing a get-all-data/store-all-data-type function for temporary revision history will actually suit my needs, if it is possible.

like image 557
Chris Cirefice Avatar asked Aug 22 '13 21:08

Chris Cirefice


People also ask

How do you undo in Google spreadsheet?

Press Ctrl + Z. Your last action is undone. For example, if you had deleted an item and then decided you wanted to keep it after all, undo would make it reappear. Click the Redo button on the toolbar to redo the last action.


1 Answers

I had a similar problem when I needed to protect the sheet yet allow edits via a sidebar. My solution was to have two sheets (one hidden). If you edit the first sheet, this triggers the onEdit procedure and reloads the values from the second sheet. If you unhide and edit the second sheet, it reloads from the first. Works perfectly, and quite entertaining to delete data on mass and watch it self repair!

like image 138
John Moore Avatar answered Dec 28 '22 10:12

John Moore