AWS Lambda e API Gateway
API Gateway é um serviço da AWS para criar, publicar, manter e monitorar de maneira muito simples APIs REST ou Web Socket que servem como porta de entrada para serviços que operam no back-end como acesso ao banco de dados, processamento de regras de negócios e diversas outras funcionalidades.
APIs REST são baseadas no protocolo HTTP e implementam os métodos padrões deste protocolo tais como GET, PUT, POST, DELETE e PATCH.
Neste artigo fazemos uma introdução a API Gateway com REST endpoints chamando outro serviço AWS no back-end, neste caso AWS Lambda.
AWS Lambda
Lambda é outro serviço da AWS que permite executar um código baseado em algum evento. O diferencial do Lambda é que ele é sevrerless, ou seja, você apenas cria sua lógica e a AWS cuida de toda infraestrutura necessária como escalonamento, memória, processamento, etc. Lambdas são como funções que rodam na nuvem, cujo código pode ser disparado sob diversas formas.
API Gateway + Lambda
Um caso de uso muito comum é integrar os serviços API Gateway e Lambdas, de modo que a chamada ao primeiro dispare a execução da lógica no segundo. Como exemplo dessa integração:- Criamos uma função Lambda que cria um JSON e o retorna (parte 1)
- Um REST endpoint via API Gateway que chama a função e retorna seu resultado (parte 2)
Para executar o exemplo é necessário que você tenha pelo menos uma conta gratuita na AWS e instalar a ferramenta AWS CLI, que permite gerenciar os serviços da AWS por linha de comando.
Criando o Lambda
Utilizando sua IDE de preferencia (neste exemplo uso o INteliJ), crie um projeto MAVEN. O arquivo pom.xml contém as dependencias para se trabalhar com o Lambda e manipulação de JSON com a API gson google:
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.finalexception</groupId>
<artifactId>LambdaApiGatewayP01</artifactId>
<version>1.0</version>
<name>lambda-api</name>
<properties>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
<dependencies>
<dependency>
<groupId>com.google.code.gson</groupId>
<artifactId>gson</artifactId>
<version>2.8.6</version>
</dependency>
<dependency>
<groupId>com.amazonaws</groupId>
<artifactId>aws-lambda-java-core</artifactId>
<version>1.1.0</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-shade-plugin</artifactId>
<version>2.3</version>
<configuration>
<createDependencyReducedPom>false</createDependencyReducedPom>
</configuration>
<executions>
<execution>
<phase>package</phase>
<goals>
<goal>shade</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>
O plugin maven-shade permite compactar todas as dependencias junto com o jar final. Isso será necessário ao subir o arquivo compactado do projeto para executá-lo na nuvem.
Crie um pacote chamado service.lambda e crie classe Function01 cujo código é o que segue:
A partir da raiz do seu projeto, rode o comando mvn clean package para empacotar o projeto, gerando o arquivo LambdaApiGatewayP01-1.0.jar
Fazendo o deploy do arquivo na AWS
Agora vamos enviar o arquivo do projeto para o serviço AWS Lambda. A partir da raiz do seu projeto, execute o seguinte comando:
O valor do parâmetro --role deve ser qualquer role na sua conta AWS que tenha autorização para criar Lambdas. Quando você cria uma conta, no mínimo deve ter a role administrador, que possui todas as permissões.
Após criar a função, é retornado um JSON contendo várias propriedades da mesma. Observe e copie o valor da propriedade functionArn, representa o endereço dessa função específica no ambiente AWS. Ao invocar essa função, utilizaremos o valor desse functionArn.
Agora que você publicou a função, faça um teste invocando-a. Substitua o valor de functionArn perlo valor gerado na sua conta:
O parâmetro /tmp/outfile contém a resposta gerada pela função no formato JSON. Você pode checá-lo abrindo o arquivo:
Na segunda parte intergamos essa função com um endpoint REST via API Gateway. Dessa forma, requisições HTTP no endpoint farão a função disparar.
Referências:
https://aws.amazon.com/lambda/
https://aws.amazon.com/api-gateway/
Crie um pacote chamado service.lambda e crie classe Function01 cujo código é o que segue:
package service.lambda;
import com.amazonaws.services.lambda.runtime.Context;
import com.amazonaws.services.lambda.runtime.RequestStreamHandler;
import com.google.gson.JsonObject;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.OutputStreamWriter;
public class Function01 implements RequestStreamHandler{
@Override
public void handleRequest(InputStream inputStream, OutputStream outputStream, Context context) throws IOException
{
//API para manipulacao de JSONs
JsonObject responseJson = new JsonObject();
JsonObject responseBody = new JsonObject();
JsonObject headerJson = new JsonObject();
//propriedade mensagem na resposta
responseBody.addProperty("message", "it's everything OK here!");
// um header aleatório na resposta para API Gateway
headerJson.addProperty("x-custom-header", "my custom header value");
// Http status code 200 OK
responseJson.addProperty("statusCode", 200);
responseJson.add("headers", headerJson);
responseJson.addProperty("body", responseBody.toString());
// serializa o JSON para um OutputStream
OutputStreamWriter writer = new OutputStreamWriter(outputStream, "UTF-8");
writer.write(responseJson.toString());
writer.close();
}
}
A partir da raiz do seu projeto, rode o comando mvn clean package para empacotar o projeto, gerando o arquivo LambdaApiGatewayP01-1.0.jar
Fazendo o deploy do arquivo na AWS
Agora vamos enviar o arquivo do projeto para o serviço AWS Lambda. A partir da raiz do seu projeto, execute o seguinte comando:
aws lambda create-function --function-name funcao01 \
--zip-file fileb://target/LambdaApiGatewayP01-1.0.jar \
--handler service.lambda.Function01::handleRequest \
--runtime java8 \
--role arn:aws:iam::12121212121:role/developer
O valor do parâmetro --role deve ser qualquer role na sua conta AWS que tenha autorização para criar Lambdas. Quando você cria uma conta, no mínimo deve ter a role administrador, que possui todas as permissões.
Após criar a função, é retornado um JSON contendo várias propriedades da mesma. Observe e copie o valor da propriedade functionArn, representa o endereço dessa função específica no ambiente AWS. Ao invocar essa função, utilizaremos o valor desse functionArn.
Agora que você publicou a função, faça um teste invocando-a. Substitua o valor de functionArn perlo valor gerado na sua conta:
aws lambda invoke --function-name arn:aws:lambda:us-east-1:205303771310:function:funcao01 \
--invocation-type RequestResponse /tmp/outfile.txt
O parâmetro /tmp/outfile contém a resposta gerada pela função no formato JSON. Você pode checá-lo abrindo o arquivo:
Na segunda parte intergamos essa função com um endpoint REST via API Gateway. Dessa forma, requisições HTTP no endpoint farão a função disparar.
Referências:
https://aws.amazon.com/lambda/
https://aws.amazon.com/api-gateway/
"Quanto a vocês, não fiquem procurando o que vão de comer e o qque vão beber. Não fiquem inquietos. Porque são os pagãos deste mundo que procuram tudo isso. O Pai bem sabe que vocês têm necessidade dessas coisas. Portanto, busquem o Reino dele, e Deus dará a vocês essas coisas em acréscimo. Não tenha medo, pequeno rebanho, porque o Pai de vocês tem prazer em dar-lhes o Reino"
Lucas 12:29-31
para criar esse projeto no eclipse usaria qual configuração para startar o projeto
ReplyDeleteprojeto maven normal, pra qualquer IDE
Deletena verdade seria o Archetype
Deletepor que no eclipse pede para selecionar um e no vídeo não mostra qual.
GroupId: org.apache.maven.archetypes
ReplyDeleteArtifactId: maven-archetype-quickstart
Version: 1.4
Repository URL: https://repo1.maven.org/maven2