Как можно улучшить мой замороженный скрипт резервного копирования, чтобы избежать тайм-аута? - PullRequest
2 голосов
/ 12 ноября 2019

У меня есть сценарий резервного копирования, который работает (ниже), но время ожидания истекло из-за большого количества строк и формул. Сценарий заключается в создании замороженной резервной копии с использованием только значений (без формул) всей электронной таблицы (или нескольких листов). Я пытаюсь улучшить его, не копируя листы с формулами в новую электронную таблицу, а только копируя «замороженные» копии этих листов. Буду признателен за любую помощь / руководство.

Сценарий, приведенный ниже, прекрасно работает с электронной таблицей, в которой не слишком много строк и формул. Я пытался изменить его, используя SpreadsheetApp.create вместо .copy для создания пустой электронной таблицы, а затем пытался придумать, как использовать метод .forEach с оператором if для идентификации _temp листов итолько скопируйте их. Я застрял на некоторое время, отсюда и этот вопрос.

Текущий сценарий:

function copyEntireSpreadsheet() {
  var id = "ID"; // Please set the source Spreadsheet ID.

  var ss = SpreadsheetApp.openById(id);
  var srcSheets = ss.getSheets();
  var tempSheets = srcSheets.map(function(sheet, i) {
    var sheetName = sheet.getSheetName();
    var dstSheet = sheet.copyTo(ss).setName(sheetName + "_temp");
    var src = dstSheet.getDataRange();
    src.copyTo(src, {contentsOnly: true});
    return dstSheet;
  });
  var destination = ss.copy(ss.getName() + " - " + new Date().toLocaleString());
  tempSheets.forEach(function(sheet) {ss.deleteSheet(sheet)});
  var dstSheets = destination.getSheets();
  dstSheets.forEach(function(sheet) {
    var sheetName = sheet.getSheetName();
    if (sheetName.indexOf("_temp") == -1) {
      destination.deleteSheet(sheet);
    } else {
      sheet.setName(sheetName.slice(0, -5));
    }
  });
}

Срок действия приведенного выше сценария истек, поскольку в новой (скопированной) электронной таблице он занимает слишком много времениобрабатывать все ячейки с формулами, но в первую очередь не нужно их копировать.

Приведенный выше скрипт работает следующим образом:

  1. Создание копий всех листов и переименование сдобавление "_temp".
  2. Перезаписывает каждый лист "_temp" на себя с параметром contentsOnly: true, чтобы формулы стали значениями.
  3. Создает копию всей электронной таблицы.
  4. Удаляет листы «_temp» из исходной электронной таблицы.
  5. Удаляет исходные листы из целевой таблицы.

Что я хотел бы выполнить:

  1. Создайте копии всех листов ("_temp") и перепишите сами, чтобы избавиться от формул. (1 и 2 выше)
  2. Создание пустой электронной таблицы (новая)
  3. Копирование только листов "_temp" в новую электронную таблицу (новую)
  4. Удаление листов "_temp" висходная электронная таблица (4 выше)

Если я смогу изменить ее так, чтобы я мог определить, какие листы следует скопировать, это было бы еще лучше, но простая копия всех листов _temp также сделаетработа.

Заранее спасибо за любую помощь!

Final Script

@ Ответ Танаике был быстрым и простым - работал отлично! Добавлен .slice для удаления текста "_temp" с новых скопированных листов. Вот финальный скрипт для тех, кто ищет похожий скрипт:

function copyEntireSpreadsheetTest() {
  var id = "ID"; // Please set the source Spreadsheet ID.

  var ss = SpreadsheetApp.openById(id);
  var srcSheets = ss.getSheets();
  var tempSheets = srcSheets.map(function(sheet, i) {
    var sheetName = sheet.getSheetName();
    var dstSheet = sheet.copyTo(ss).setName(sheetName + "_temp");
    var src = dstSheet.getDataRange();
    src.copyTo(src, {contentsOnly: true});
    return dstSheet;
  });

  var destination = SpreadsheetApp.create(ss.getName() + " - " + new Date().toLocaleString());
  tempSheets.forEach(function(sheet) {
    sheet.copyTo(destination).setName(sheet.getSheetName().slice(0,-5));
    ss.deleteSheet(sheet);
  });
  destination.deleteSheet(destination.getSheets()[0]);
}

1 Ответ

1 голос
/ 12 ноября 2019
  • Чтобы изменить следующий сценарий, измените сценарий.

    1. Создайте копии всех листов ("_temp") и перепишите сами, чтобы избавиться от формул. (1 и 2 выше)
    2. Создание пустой электронной таблицы (новая)
    3. Копирование только листов "_temp" в новую электронную таблицу (новую)
    4. Удаление листов "_temp" висходная электронная таблица (4 выше)

Если моё понимание верно, как насчет этой модификации?

От:

var destination = ss.copy(ss.getName() + " - " + new Date().toLocaleString());
tempSheets.forEach(function(sheet) {ss.deleteSheet(sheet)});
var dstSheets = destination.getSheets();
dstSheets.forEach(function(sheet) {
  var sheetName = sheet.getSheetName();
  if (sheetName.indexOf("_temp") == -1) {
    destination.deleteSheet(sheet);
  } else {
    sheet.setName(sheetName.slice(0, -5));
  }
});

До:

var destination = SpreadsheetApp.create(ss.getName() + " - " + new Date().toLocaleString());
tempSheets.forEach(function(sheet) {
  sheet.copyTo(destination).setName(sheet.getSheetName());
  ss.deleteSheet(sheet);
});
destination.deleteSheet(destination.getSheets()[0]);

Ссылка:

Если я неправильно понял ваш вопрос, и это не былоРезультат, который вы хотите, я прошу прощения.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...