/**
* @file A snippet for deleting rows from a Google Sheet by condition.
* Examples of the snippet
* {@link https://webapps.stackexchange.com/a/133308/}
* {@link https://groups.google.com/forum/#!topic/google-apps-script-community/-ITmOCfJmFw}
* {@link https://toster.ru/q/690651}
*/
/**
* Removes rows from a sheet according to the condition
*
* @function
* @name deleteRowsByConditional_
* @example
* // Removes all rows where B column contains 10
* deleteRowsByConditional_(SpreadsheetApp.getActiveSheet(),
* function(currentValue){
* return currentValue[1] === 10;
* }
* );
*
* @param {Sheet} sheet - Represents the Sheet that is changing.
* @param {conditionCallback} condition - The callback that should return true/false state for each row.
* @param {dataCallback} action - The callback that exec with current removed rows.
**/
function deleteRowsByConditional_(sheet, condition, action) {
sheet
.getDataRange()
.getValues()
.forEach(
(_, i, arr) => {
const j = arr.length - i - 1;
if (this.condition.apply(null, [arr, j])) {
this.isContinue++;
if (j > 0) return;
}
if (this.isContinue > 0) {
const prevPos = j + 1;
if (action) action(arr, prevPos, this.isContinue);
this.sheet.deleteRows(prevPos + 1, this.isContinue);
this.isContinue = 0;
return;
}
return;
},
{ sheet: sheet, condition: condition, isContinue: 0 }
);
}
/**
* Returns true/false state for each row.
*
* @callback conditionCallback
* @param {Array} array - The DataRange.
* @param {number} index - The index of the current row.
* @return {boolean}
**/
/**
* Exec with current removed rows.
*
* @callback dataCallback
* @param {Array} array - The DataRange.
* @param {number} index - The index of the current row.
* @param {number} index2 - The index2 of the current row.
* @return {any}
**/
/* global deleteRowsByConditional_ */
/**
* Runs the snippet.
* Removes rows from an active sheet by condition 'B:B=10'
*/
function run1() {
const sheet = SpreadsheetApp.getActiveSheet();
deleteRowsByConditional_(sheet, (values, i) => values[i][1] === 10);
}
/**
* Runs the snippet.
* Removes rows by condition '(A:A<>"")*(B:B<>"")*(D:D<>"")*(F:F<>"")'.
* Appends deleted rows to the 'Archive' sheet.
*
* @see https://toster.ru/q/690651
*
*/
function run2() {
const sheet = SpreadsheetApp.getActiveSheet();
if (sheet.getName() === 'Archive') return;
const archive = SpreadsheetApp.getActive().getSheetByName('Archive');
const action = (values, i, i2) => {
const data = values.slice(i, i + i2);
archive
.getRange(archive.getLastRow() + 1, 1, data.length, data[0].length)
.setValues(data);
};
const condition = (values, i) => {
const row = values[i];
return (
i > 0 && row[0] !== '' && row[1] !== '' && row[3] !== '' && row[5] !== ''
);
};
deleteRowsByConditional_(sheet, condition, action);
}