DevGang
Авторизоваться

CRM с Lambda и Terraform

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

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

Технологии, которые мы будем использовать, следующие:

  1. Terraform (IaC — предоставление ресурсов)
  2. AWS Lambda (вычислительная инфраструктура на AWS)
  3. HubSpot API (для сохранения запросов)

Структура

Начнем с создания нового рабочего каталога

mkdir contact-us
cd contact-us

План здесь состоит в том, чтобы создать минимальную лямбда-функцию, которая сохраняет пользовательские данные из клиентского приложения (веб-сайт WordPress, Wix, пользовательский клиентский веб-сайт и т. д.) в нашу CRM HubSpot. Итак, давайте приступим прямо к делу.

План

Мы начнем с подготовки нашей лямбда-функции из Terraform.

touch main.tf providers.tf outputs.tf variables.tf

provider.tf — этот файл предназначен для определения провайдеров Terraform, которых мы хотим использовать.
main.tf — в этом файле будет находиться наша логика предоставления ресурсов (если это большое приложение, мы создадим отдельные файлы модулей).
variable.tf — этот файл предназначен для определения переменных, необходимых для нашего модуля terraform.
outputs.tf — любые выходные данные, которые нам нужны после предоставления наших ресурсов.

Нам нужно будет загрузить реестр Terraform нашего провайдера AWS в файл provider.tf вместе с вашим ключом доступа к AWS и секретным ключом (подробнее о том, как сгенерировать эти ключи, читайте здесь).

providers.tf
# providers.tf
terraform {
  required_providers {
    aws = {
      source  = "hashicorp/aws"
      version = "5.8.0"
    }
  }
}

provider "aws" {
  region     = var.aws_region
  access_key = var.access_key
  secret_key = var.secret_key
}
variables.tf
# variables.tf
variable "aws_region" {
  type        = string
  description = "AWS Region"
  default     = "eu-west-1"
}

variable "secret_key" {
  type        = string
  description = "AWS Secret Key"
}


variable "access_key" {
  type        = string
  description = "AWS Access Key"
}

Для планирования нашей лямбда-функции мы будем использовать лямбда-модуль terraform, а не ресурс, поэтому при повторном использовании мы можем просто использовать этот конкретный модуль.

module "lambda" {
  source        = "terraform-aws-modules/lambda/aws"
  version       = "5.2.0"
  function_name = "contact-us"
  architectures = ["arm64"]
  runtime       = "nodejs18.x"
  handler       = "index.handler"

  attach_policy_statements = true

  policy_statements = {
    AmazonSSMReadOnlyAccess = {
      sid       = "AmazonSSMReadOnlyAccess"
      effect    = "Allow"
      actions   = ["ssm:Describe*", "ssm:Get*", "ssm:List*"]
      resources = ["*"]
    }
  }

  source_path = [{
    path = "${path.module}/functions/contact-us"
  }]

  create_lambda_function_url = true

  cors = {
    allowed_credentials = false
    allowed_headers     = ["*"]
    allowed_methods     = ["POST", "OPTIONS", ]
    allowed_origins     = ["*"] # We would only want to allow our domain here
    max_age_seconds     = 3000
  }
}

Итак, давайте пройдемся по входным данным построчно. Сначала мы определяем, какой источник мы используем из модуля terraform и его версию. Затем мы определяем, какую архитектуру, язык программирования и среду выполнения мы используем для лямбда-функции. Для разрешений мы используем встроенные операторы политики, в которых мы разрешаем доступ к хранилищу параметров SSM, поскольку мы не хотим напрямую хранить ключи API HubSpot в лямбда-функции и будем хранить их в хранилище параметров. Мы хотим создать URL-адрес лямбда-функции, который мы можем вызывать напрямую, поэтому мы отмечаем true для create_lambda_function_url (это не самый идеальный способ, подробнее об этом позже), за которым следует CORS config.

Запустим terraform init и получим нужных провайдеров.

Terraform has been successfully initialized!

You may now begin working with Terraform. Try running "terraform plan" to see
any changes that are required for your infrastructure. All Terraform commands
should now work.

If you ever set or change modules or backend configuration for Terraform,
rerun this command to reinitialize your working directory. If you forget, other
commands will detect it and remind you to do so if necessary.

Отлично! Теперь настроим HubSpot.

HubSpot

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

В приложении hubspot мы можем создать свое собственное частное приложение (которое похоже на подключенное приложение, если вы когда-либо использовали SalesForce или думали о нем как о клиенте), а затем выберите crm.objects.contacts доступ для чтения/записи. Вот и все! Затем мы получаем собственный ключ доступа к HubSpot.

Затем мы сохраним этот ключ в нашем хранилище параметров AWS и сохраним его в виде зашифрованной строки.

Вот и все! Теперь мы приступаем к кодированию фактической лямбда-функции.

Лямбда

Мы создадим новую папку с именем functions, а затем подпапку с именем contact-us. Здесь будет находиться лямбда-функция. Там мы создадим файл package.json используя yarn init -y и создадим пустой index.js со следующим содержимым.

const handler = async (event, context) => {};

module.exports = { handler };

Мы установим 3 библиотеки: @aws-sdk/client-ssm для получения ключа доступа к HubSpot и @hubspot/api-client для взаимодействия с HubSpot API.

yarn add @aws-sdk/client-ssm @hubspot/api-client 

и вот как выглядит наш index.js

const AWS = require("@aws-sdk/client-ssm");
const hubspot = require("@hubspot/api-client");

const handler = async (event, context) => {
  const body = JSON.parse(event.body);

  const ssm = new AWS.SSM({
    region: "eu-west-1",
  });

  const hubspot_key = await ssm.getParameter({
    Name: "HUBSPOT_ACCESS_KEY",
    WithDecryption: true,
  });

  const hubspot_access_key = hubspot_key.Parameter.Value;

  const hubspotClient = new hubspot.Client({
    accessToken: hubspot_access_key,
  });

  await hubspotClient.crm.contacts.basicApi.create({
    properties: {
      email: body.email,
      firstname: body.firstname,
      lastname: body.lastname,
      phone: body.phone,
      message: body.message,
    },
  });

  return {
    statusCode: 200,
    body: JSON.stringify({
      message: "Thanks for contacting us! We will be in touch soon.",
    }),
  };
};

module.exports = { handler };

Теперь, прежде чем мы приступим к terraform plan, чтобы увидеть изменения, которые он собирается внести, сначала нам нужно создать main.tfvars, а затем предоставить ключ доступа AWS и секретный ключ, но лично у меня в моей личной организации включен IAM Identity Center, поэтому я пропущу это.

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

Итак, давайте протестируем недавно созданную лямбда-функцию на Postman.

Отлично! Мы успешно развернули нашу лямбда-функцию, и если мы перейдем к HubSpot, мы также увидим добавленный там новый контакт.

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

Улучшения

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

  1. Мы бы не использовали URL-адрес лямбда-функции в качестве собственной конечной точки в большом приложении. Вместо этого мы можем создать API-шлюз, который выходит на лямбда-функцию, и установить их в качестве целей.
  2. Если мы хотим, чтобы запросы уведомляли нас, мы можем либо добавить службу SES, либо Slack API, чтобы получать уведомления в нашем собственном канале.
  3. Настройка конвейеров CD для лямбда-функции при развертывании — еще одна вещь, которую можно улучшить.
  4. В реальном приложении, где есть множество маршрутов в шлюзе API, мы не будем использовать только один файл Terraform для их развертывания. У нас будет специальная файловая структура для работы с разными состояниями Terraform для разных функций и ресурсов.

Итак, это конец этой маленькой лаборатории. Я надеюсь, вам, ребята, понравилось, и я надеюсь увидеть вас в следующем блоге! Чао!

Ссылка на репозиторий Github: https://github.com/halchester/contact-us-lambda-hubspot

Источник:

#Cloud #AWS
Комментарии
Чтобы оставить комментарий, необходимо авторизоваться

Присоединяйся в тусовку

В этом месте могла бы быть ваша реклама

Разместить рекламу