Как мы достигли предела возможностей Google Docs

Простым смертным иногда кажется, что компании вроде Google, Apple и Amazon — бесконечно сильные исполины. Они ежедневно таскают на своих плечах все свои сервисы, доступные практически каждому человеку на планете, а каждый пользователь, в свою очередь, имеет безграничный доступ к вычислительным ресурсам этих компаний.

Отчасти это так. Тот же Google в секунду обрабатывает количество запросов, которое, кажется, у нормального человека в голове уложиться не может. И такой сервис у него (и не только у него) — не один.

При повседневном использовании мы редко приближаемся к ограничениям, установленным то здесь, то там, чтоб наплыв пользователей в одну точку случайно не положил весь сервис в целой стране или даже регионе. Или не случайно, но об этом лучше расскажут безопасники.

Мы в «Собаке Павловой» начали строить дизайн-задачник на базе Google Spreadsheet. Мы смогли реализовать на них все, что хотели, оставаясь в парадигме No-code. Если не слышали — это когда продукт строится без кода и толп программистов, на специальных сервисах. Небольшие скрипты, написанные кодом, не в счет.

Всеядность и стабильность работы Таблиц нас настолько впечатлили, что особых проблем с масштабируемостью мы не ожидали. Но уже при первом массовом запуске студентов на обучение поняли, что зря. У всех иногда лапки, и у таблиц Google тоже.

Не IMPORTRANGEм единым

Часть конструкций в нашем задачнике живет благодаря возможности передавать данные из определенных ячеек и диапазонов из одной таблицы в другую — с помощью формулы IMPORTRANGE. Так мы раздаем содержимое задач в таблицы студентов, немного усложняем жизнь последователям Робин Гуда и собираем данные для статистики.

Когда нагрузка небольшая, задачники работают отлично: данные подтягиваются достаточно быстро, ничего не сбоит и вообще все максимально красиво. Но как только нагрузка увеличивается — начинается ой.

#REF!

Пока не будем вдаваться в подкапотные тонкости ошибки, расскажем о них позже. Но результат у нее очень интересный — если IMPORTRANGE не смог получить содержимое ячеек, на которые ссылается, то он ничего не вернет. Вообще. И руками повторно запустить отвалившуюся формулу не получится, вместо значения будет гордо красоваться пустая ячейка.

Вот такая

Чаще всего эти ошибки возникают точечно, и почти всегда помогает еще раз загрузить таблицу — данные подтянутся. Но иногда вылезают совсем интересные баги. Например, в формуле, которая ссылается на упавшую ячейку, появлялся #REF ! (как при удалении ячейки), убивая содержимое этой формулы. То есть вместо формулы появляется постоянное (текстовое) значение, которое нужно убирать вручную.

Возможные решения

  1. Оберните формулу в IFERROR(). Тогда при появлении ошибки Google попробует выполнить операцию повторно. Некоторые советуют провернуть эту операцию несколько раз.

  2. Ошибка напрямую зависит от размера таблиц и диапазона, который импортируется. Попробуйте удалить лишние строки и лишнее условное форматирование или уменьшить размер диапазона.

300 спартанцев

Опытным путем мы выяснили, что проблемы начинаются, когда в одной таблице появляется больше 300 формул с IMPORTRANGE на разные файлы. Есть подозрение, что проблема — в большом количестве обращений к таблицам из одного места. Похожих проблем, когда таблица обращается к меньшему количеству файлов, но несколько раз, мы не нашли. Но возможно, там тоже есть что-то подобное. Если ссылаться на один файл из разных мест — такая ошибка не появляется.

AppScripts

Часть автоматизации задачника выполняется на базе Google AppScripts — облачной песочницы с JS-based языком. Она позволяет работать с таблицами (и другими продуктами Google) вне их графической оболочки и автоматизировать рутинные процессы.

Хотя сервис очень мощный, на технические ограничения мы наткнулись практически сразу, как начали его использовать. Часть из них явно ввели намеренно, но некоторые — похожи на недоработки, и хочется надеяться, что когда-нибудь их поправят.

Тайминг

Скрипт выполняется только 30 минут. Иногда чуть больше, но мы списали это на погрешность времени запроса к файлам. Когда скрипт отработал полчаса — он просто останавливается, а в консоли появляется соответствующая ошибка. Если скрипт перезапустить, он начнет работу с начала. Возможности перезапустить скрипт и продолжить выполнение мы не нашли.

Это нужно, очевидно, чтоб убивать случайно запущенные бесконечные скрипты. Ну и чтобы не было соблазна писать на скриптах огромные программы. Так или иначе, ограничение приходится учитывать.

Интересно то, что и из этого правила есть исключение. Однажды скрипт проработал почти 44 минуты и даже успешно выполнился. Но он такой был один, поэтому мы решили, что ему просто повезло

При этом похоже, что он запустился дважды в одно выполнение

Вариант решения

Если очень сильно заморочиться, то можно сохранять в служебной таблице текущее состояние скрипта. При запуске проверять, что он уже сделал, и запускать с нужного места.

Неравномерность выполнения

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

Между выполнениями интервал 1 час

Вдобавок скорость загрузки данных из документа зависит от его объема. В случае с таблицами — размер таблиц, объем данных и дополнительные данные таблиц (правила, скрипты и т.д.). В задачнике студенческие таблицы одинаковые по размеру, а объем данных меняется в рамках погрешности. Но это стоит учитывать, если вы работаете с разноплановыми документами.

Возможные решения

  1. Старайтесь держать документы в актуальности и порядке. Удаляйте лишние данные и пустые строки.

  2. Сделайте 3-5 тестовых прогона скрипта, добавьте к среднему времени выполнения 30%. Этого должно хватить на случай сбоев на стороне Google.

  3. Если скрипт выполняется дольше 30 минут — попробуйте разделить данные на несколько скриптов или используйте промежуточные таблицы.
  4. Проведите ревью кода и постарайтесь уменьшить число повторяющихся запросов к документам.

Отваливается и тут

Выше мы уже рассказывали при ошибке importrange вместо формулы подставляется #REF !. Немного покопались в мануалах и нашли там возможность на AppScripts написать собственную формулу. Заподозрили, что формулы встроенные тоже работают на скриптах. Но эта мысль скорее для фанатов теории заговора.

Так или иначе, иногда скрипт просто отваливается посреди выполнения. Объясняет свое поведение двумя причинами:

  • «Сервису "Таблицы" недоступен документ “ID таблицы”»

  • «Слишком много одновременных вызовов: Таблицы»
Так
Или так

Обе ошибки появляются настолько рандомно, что найти их причину невозможно. У нас параллельно запущено пять скриптов для разных потоков студентов, и, возможно, иногда это вызывает вторую ошибку. Но в 95% выполнений все проходит отлично при тех же вводных. Первая ошибка — вообще загадка.

Интересно, что если скрипт не использует формулу, то он не убивает неполученные данные, а возвращает пустую строку. Мы предусмотрели это, и если скрипт получает пустые данные, он просто пропускает эту итерацию, оставляя предыдущее значение. Можно было сделать и повторный запрос, но:

  • мы рисковали бы создать бесконечный цикл;

  • у нас все еще ограничение по времени выполнения скрипта, в которое мы укладываемся впритык.

Варианты решения

Никаких. Просто жаловаться на Google в профильных ветках и учитывать эти особенности при разработке нагруженных скриптов.

Тонкая работа

Самый редкий кейс — в AppScripts при работе с таблицами нельзя удалить правило условного форматирования. Можно создать, изменить, применить к диапазону. Удалить — нет. А так как у нас на форматировании построена немалая часть задачника, получилось особенно больно.

Похожая история и с правилами проверки данных, но там еще хуже — их нельзя даже редактировать. Только танец с бубном в виде создания изменяемой копии правила.

Вариант решения

Удалите из правила все диапазоны, для которых оно применяется. Плюсы: правило больше не будет применяться. Минусы: вы намусорили в таблице.

Вместо титров

No-code в нашем случае отлично показал себя. Он кратно удешевляет создание MVP и первых версий продуктов и позволяет любому члену команды создавать новые фичи. Но это не волшебная таблетка, которая все сделает за вас, и технические проблемы все равно придется решать вручную.

Уверены, ограничений и недоработок у Google кратно больше. Уверены, что часть наших проблем уже кто-то решил. Уверены, что с оставшимися вполне можно жить.

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

0
16 комментариев
Написать комментарий...
Alexandr Svetlov

мыши плакали, кололись, но продолжали грызть кактус

Ответить
Развернуть ветку
Максим Петров

чем больше будут накатывать на этот нон-код, создавая вавилонские башни, тем сильнее будет обратным откат:)

Ответить
Развернуть ветку
Murat Ondasyn

Ору с комента ))))

Ответить
Развернуть ветку
Аккаунт удален

Комментарий недоступен

Ответить
Развернуть ветку
Семен Смирнов

Авторы решили использовать неподходящий инструмент, стоящий небольшие деньги, для большого заработка

Причём ограничения на используемые функции явно описаны в документации

Конец немного предсказуем. Причём есть попытки подать конец как несовершенство инструмента, а не странную логику авторов

Ответить
Развернуть ветку
Аккаунт удален

Комментарий недоступен

Ответить
Развернуть ветку
Николай

Делал в sheets таблицу для личного пользования, так вот там было около 50 запросов "importxml" - пользоваться было нереально, эти запросы тупили при каждом входе.

Ответить
Развернуть ветку
Семен Смирнов

Функции импорта - самые затратные для Таблиц. 50 это вообще лимит на документ
Это все равно что загрузить AWS на 100% и удивляться производительности

Ответить
Развернуть ветку
Ol Ka
У всех иногда лапки, и у таблиц Google тоже.

Я айтишный не очень понимаю — может кто-нибудь на русский перевести, пожалуйста 😶

Ответить
Развернуть ветку
Boris

Это не айтишное, это трехлетний мем —- https://memepedia.ru/ne-mogu-u-menya-lapki/

Ответить
Развернуть ветку
Ol Ka

Да, мне врач сказал уже, что у меня мемная недостаточность.

Спасибо за ссылку. С Наступающим!

Ответить
Развернуть ветку
Alexander Margolen

Google Spreadsheets все-таки несколько не для того создан, как автор пытается их использовать. Не для постоянного использования собственных скриптов, не связанных с интерфейсом, и сотни функций ImportRange.
Без понятия, почему не верстанули для своих собственных целей простой сайт, тем более, судя по тому, что преподают, должны это уметь. Но в голове возникает картинка дома из костылей.

Хотя так как я человек, использующий Google Spreedsheet как вспомогательную программу для текстового редактора, писать это несколько двулично с моей стороны...

Ответить
Развернуть ветку
Семен Смирнов

Почему нет

Гугл даёт халявные серверные мощности и табличный процессор с полноценной (особенно после недавнего апдейта) ide. Во многих вопросах всякие power bi не нужны, хватает и гугла

Главное не наглеть и не пытаться в большой бизнес

Ответить
Развернуть ветку
Konstantin Loban

Я тоже в своей работе столкнулся с тормознутой работой. Связываю это с большим взаимодействием между разными листами одной таблицы, которые для GSheets, по-видимому, как разные файлы. Так же обратил внимание, что кастомные функции, написанные на AppScript потом выполняются совсем не в приоритете, что тоже отражается на времени выполнения. А еще ARRAYFORMULA, которая всегда выполняется с особой степенью задумчивости, особенно при количестве строк 300+... Ну в общем, облачность, конечно решает, но если честно, неоднократно возникало желание конвертировать мой AppScript в VB для LibreOffice. Кстати, я думаю, что часть проблем решило бы, если бы goggle сделало десктопный вариант приложения, где все вычисления оффлайново ложились на клиента, а потом просто происходила периодическая синхронизация с облаком.

Ответить
Развернуть ветку
Дмитрий Удинский

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

Ответить
Развернуть ветку
Eugeny N

Привет, вы пишите про 30 минут выполнения скрипта, но квота максимального времени выполнения скрипта https://developers.google.com/apps-script/guides/services/quotas 6 минут, после этого скрипт останавливается автоматически. Как вы добились 30 минут?

Ответить
Развернуть ветку
13 комментариев
Раскрывать всегда