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

Однако огромное разнообразие инструментов и показателей, необходимых нашим клиентам, делает нашу платформу интеграции одной из самых серьезных инженерных проблем!

Как мы можем предоставить точные и актуальные данные для большого портфеля интеграций? В некоторых случаях даже получить данные непросто, так как часто числа недоступны через API службы, и их необходимо вычислить. А еще есть бремя обслуживания. Как вы справляетесь с изменением API, отслеживая ошибки и эффективно внедряя новые функции при каждой интеграции?

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

В результате даже когда у нас была интеграция с сервисом, он не поддерживал фактическую метрику, которую хотел клиент!

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

Уроки истории

Еще до того, как мы начали проект, меня поразило, что существуют аналогии между проблемой, которую мы пытались решить, и реляционными базами данных. Это был неортодоксальный подход, но я начал этот проект, погрузившись в массу академических исследований 1970-х годов. Это оказалось бесценным. 70-е годы были революционным периодом в компьютерных науках, и я начал с чтения статьи Эдгара Ф. Кодда 1970 года, в которой показано, как можно получить доступ к информации, хранящейся в больших базах данных, не зная, как эта информация была структурирована или где она находилась в базе данных.

Я начал думать: что, если данные, с которыми мы имеем дело, не были скрыты за сторонним API, а вместо этого были в базе данных, которую мы контролировали? Операции, которые мы хотели выполнить с нашей интеграцией, были теми же, что и в реляционной базе данных или с SQL.

Затем я начал читать статьи о первых типах реляционных баз данных. Одна статья, опубликованная IBM в 70-х годах о системе баз данных под названием System R, была особенно полезной. System R была, по сути, первой базой данных, которая действительно реализовала идею SQL: сравнительный запрос. Основное внимание в документе было уделено вопросу Как решить этот вопрос с выбором пути доступа? и ответом был планировщик запросов.

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

В то время это было серьезным нововведением, и почти 50 лет спустя казалось, что это был идеальный способ подумать о нашей проблеме интеграции. Следуя примеру System R, мы могли бы написать планировщик запросов и поместить его между пользователем, который хочет получить ответ на свой запрос, и сторонним API, который хранит данные.

Теоретически все это было хорошо, но как наш планировщик запросов узнает, как работать со сторонними API? Всякий раз, когда вы просматриваете документацию API, она обычно перечисляет его основные модели (объекты в сторонней системе), его конечные точки (запросы и изменения, которые могут выполняться на этих моделях) и граф отношений между его моделями (как один объект можно «соединить» с другим). Тогда перед нами стояла задача перевести эту документацию в машиночитаемый формат, чтобы наш планировщик запросов мог обращаться к нему всякий раз, когда его просили ответить на такой вопрос, как: «Сколько тикетов Zendesk мы решили на этой неделе?». Возможно ли это вообще?

Создание платформы

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

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

Хотя мы создавали общую платформу, мы начали с одной интеграции. Zendesk был одной из наших самых популярных интеграций на старой платформе, но предоставляемые нами показатели, как правило, не соответствовали требованиям наших клиентов. В то время как многие другие API-интерфейсы предоставляют вам предварительно агрегированные, предварительно вычисленные числа и метрики, Zendesk этого не делает. Поскольку мы хотели решить давнюю проблему с разбивкой на страницы API, Zendesk был очевидным выбором.

Сначала мы создали планировщик запросов, который будет производить самый наивный из возможных планов, и, поскольку мы изначально сосредоточились на Zendesk, мы разработали декларативный формат, достаточный для определения того, как работает API, чтобы получить некоторые базовые запросы и запустить их. . После этого мы упорно работали над тем, чтобы сделать наш планировщик запросов умнее и добавили набор очень сложных оптимизаций, которые гарантировали, что мы всегда придумываем лучший и наиболее эффективный план запроса. Мы также расширили «метаданные» API, чтобы полностью поддерживать некоторые из наиболее необычных конечных точек в Zendesk API.

Конечно, бэкэнд - это еще не все. Чтобы реализовать нашу мечту о возможности добавлять новые интеграции за несколько дней, а не месяцев, нам также пришлось полностью переосмыслить то, как мы строили наши интеграционные интерфейсы. Было бы не очень хорошо, если бы их все равно нужно было создавать вручную каждый раз, когда мы хотели бы интегрироваться с новым сервисом. Чтобы решить эту проблему, мы разработали и внедрили новый динамически генерируемый универсальный пользовательский интерфейс, но это совсем другая статья в блоге!

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

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

Будущее проекта Data In

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

Тогда возникает весь вопрос о кешировании! Для нас кеширование означает две вещи. Первое, о чем вы обычно думаете, когда думаете о кешировании: временное хранение данных для повышения эффективности. Мы хотим, чтобы данные наших клиентов были как можно более актуальными, сводя к минимуму количество и размер запросов, которые мы делаем к сторонним API, чтобы не нарушать ограничения скорости. Решить, что запрашивать и как это запланировать, - непростая задача.

Мы также хотим использовать кеширование для поддержки исторических данных. Допустим, вы хотите показать, сколько у вас подписчиков в Twitter. Нам очень легко зайти в Twitter API и сказать: «Скажите, сколько у меня подписчиков». Вы не можете отследить, сколько подписчиков в Твиттере у вас было с течением времени. Расширяя нашу платформу для сбора и хранения значений через регулярные промежутки времени, мы можем создавать эти недостающие наборы данных.

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

А пока набираем, так почему бы тебе не присоединиться к нам ?!