CLOVER🍀

That was when it all began.

OKD/Minishiftで、Route(HAProxy)を少し見てみる

これは、なにをしたくて書いたもの?

  • OKDにはRouteというものがあり、外部からのアクセスを受け付けてくれる
  • Routeの実体はHAProxy
  • Routeのルーティングは、Service経由ではなくPodへ直接振り分けということを最近知ったので

この内容を確認してみようと。

Route

最初にも書きましたが、OKDを使った時に外部からのリクエストを受け付ける役割を持ちます。

Routes - Networking | Architecture | OKD 3.11

Using the Default HAProxy Router - Setting up a Router | Configuring Clusters | OKD 3.11

正体は、HAProxyです。

KubernetesIngressと役割が似通っていますが、これはOpenShiftがKubernetesIngressがまだ存在しない時期に追加したもの
だからみたいですね。

Kubernetes Ingress vs OpenShift Route – Red Hat OpenShift Blog

環境

今回の環境は、こちらです。

$ minishift version
minishift v1.32.0+009893b


$ oc version
oc v3.11.0+0cbc58b
kubernetes v1.11.0+d4cacc0
features: Basic-Auth GSSAPI Kerberos SPNEGO

Server https://192.168.42.118:8443
kubernetes v1.11.0+d4cacc0

お題

デフォルトのプロジェクトにWildFlyを、別のプロジェクトを作成してKeycloakをデプロイして、それぞれにRouteを作成します。

この時、Routeがどのような構成になるか確認してみたいと思います。

確認対象のデプロイ

では、確認対象となるイメージをデプロイしていきます。

まずは、デフォルトのプロジェクトでWildFlyをデプロイします。

$ oc project
Using project "myproject" on server "https://192.168.42.118:8443".

デプロイから、Route作成まで。

$ oc run wildfly --image=jboss/wildfly
deploymentconfig.apps.openshift.io/wildfly created


$ oc scale dc wildfly --replicas=3
deploymentconfig.apps.openshift.io/wildfly scaled


$ oc expose dc wildfly --port=8080
service/wildfly exposed


$ oc expose svc wildfly
route.route.openshift.io/wildfly exposed

確認。

$ curl -s wildfly-myproject.192.168.42.118.nip.io | grep title
    <title>Welcome to WildFly</title>

Podを見てみます。

$ oc get pod
NAME              READY     STATUS    RESTARTS   AGE
wildfly-1-4bzjn   1/1       Running   0          6m
wildfly-1-f8p7n   1/1       Running   0          6m
wildfly-1-mwshd   1/1       Running   0          6m

続いて、別のプロジェクトを作成。

$ oc new-project other

Keycloakをデプロイ。

$ oc run keycloak --image=jboss/keycloak
deploymentconfig.apps.openshift.io/keycloak created


$ oc scale dc keycloak --replicas=3
deploymentconfig.apps.openshift.io/keycloak scaled


$ oc expose dc keycloak --port=8080
service/keycloak exposed


$ oc expose svc keycloak 
route.route.openshift.io/keycloak exposed

確認。

$ curl -s keycloak-other.192.168.42.118.nip.io/auth/ | grep title
    <title>Welcome to Keycloak</title>

こちらも、Podを見ておきます。

$ oc get pod
NAME               READY     STATUS    RESTARTS   AGE
keycloak-1-2vcr6   1/1       Running   0          4m
keycloak-1-drkcq   1/1       Running   0          3m
keycloak-1-l6dd5   1/1       Running   0          3m

Routeはどこに?

ところで、RouteもPodで動いているはずなのですが、どこにいるのでしょう?

答えとしては、defaultプロジェクトにいます。

$ oc get all -l router=router -n default --as system:admin
NAME                 READY     STATUS    RESTARTS   AGE
pod/router-1-t27rp   1/1       Running   0          1h

NAME                             DESIRED   CURRENT   READY     AGE
replicationcontroller/router-1   1         1         1         1h

NAME             TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)                   AGE
service/router   ClusterIP   172.30.222.218   <none>        80/TCP,443/TCP,1936/TCP   1h

NAME                                        REVISION   DESIRED   CURRENT   TRIGGERED BY
deploymentconfig.apps.openshift.io/router   1          1         1         config

HAProxyの設定を、コンテナの中に入って確認してみましょう。

$ oc exec -it router-1-t27rp -n default --as system:admin bash

プロセスを確認。

$ ps -ef      
UID        PID  PPID  C STIME TTY          TIME CMD
1001         1     0  0 11:45 ?        00:00:06 /usr/bin/openshift-router
1001       204     1  0 12:42 ?        00:00:00 /usr/sbin/haproxy -f /var/lib/haproxy/conf/haproxy.config -p /var/lib/haproxy/run/haproxy.pid -x /var/lib/haproxy/run/haproxy.sock 
1001       213     0  0 12:50 ?        00:00:00 bash
1001       218   213  0 12:50 ?        00:00:00 ps -ef

確かに、HAProxyが動いています。設定ファイルのパスも見えますね。

確認。

$ cat /var/lib/haproxy/conf/haproxy.config

設定ファイルの末尾の方を見ると、先ほど作成したWildFlyやKeycloakのPodが並んでいることが確認できます。

# Plain http backend or backend with TLS terminated at the edge or a
# secure backend with re-encryption.
backend be_http:myproject:wildfly
  mode http
  option redispatch
  option forwardfor
  balance leastconn

  timeout check 5000ms
  http-request set-header X-Forwarded-Host %[req.hdr(host)]
  http-request set-header X-Forwarded-Port %[dst_port]
  http-request set-header X-Forwarded-Proto http if !{ ssl_fc }
  http-request set-header X-Forwarded-Proto https if { ssl_fc }
  http-request set-header X-Forwarded-Proto-Version h2 if { ssl_fc_alpn -i h2 }
  http-request add-header Forwarded for=%[src];host=%[req.hdr(host)];proto=%[req.hdr(X-Forwarded-Proto)];proto-version=%[req.hdr(X-Forwarded-Proto-Version)]
  cookie c8f20c96872329a8ed693a128f26f96a insert indirect nocache httponly
  server pod:wildfly-1-mwshd:wildfly:172.17.0.10:8080 172.17.0.10:8080 cookie cc40ac8147cd260e8c3bea2b4f640adc weight 256 check inter 5000ms
  server pod:wildfly-1-f8p7n:wildfly:172.17.0.6:8080 172.17.0.6:8080 cookie 25a2778d2c27d7ca8620e3c91494384e weight 256 check inter 5000ms
  server pod:wildfly-1-4bzjn:wildfly:172.17.0.9:8080 172.17.0.9:8080 cookie 9aea0cc8ed45593daad18ab07f01950e weight 256 check inter 5000ms

# Plain http backend or backend with TLS terminated at the edge or a
# secure backend with re-encryption.
backend be_http:other:keycloak
  mode http
  option redispatch
  option forwardfor
  balance leastconn

  timeout check 5000ms
  http-request set-header X-Forwarded-Host %[req.hdr(host)]
  http-request set-header X-Forwarded-Port %[dst_port]
  http-request set-header X-Forwarded-Proto http if !{ ssl_fc }
  http-request set-header X-Forwarded-Proto https if { ssl_fc }
  http-request set-header X-Forwarded-Proto-Version h2 if { ssl_fc_alpn -i h2 }
  http-request add-header Forwarded for=%[src];host=%[req.hdr(host)];proto=%[req.hdr(X-Forwarded-Proto)];proto-version=%[req.hdr(X-Forwarded-Proto-Version)]
  cookie 18c824445b45c4533e54824c9aeb56b6 insert indirect nocache httponly
  server pod:keycloak-1-l6dd5:keycloak:172.17.0.12:8080 172.17.0.12:8080 cookie f7e33313456d7957447775f327dbd273 weight 256 check inter 5000ms
  server pod:keycloak-1-2vcr6:keycloak:172.17.0.13:8080 172.17.0.13:8080 cookie 916fd23d18eeaf13161646ab18a92609 weight 256 check inter 5000ms
  server pod:keycloak-1-drkcq:keycloak:172.17.0.14:8080 172.17.0.14:8080 cookie 224bcdd95633f7729a21a88cddff0b2c weight 256 check inter 5000ms

このRouteはHost名でルーティングしているようですが、その設定はどこでしょう?

このあたりのようですね。

$ grep use_backend /var/lib/haproxy/conf/haproxy.config              
  use_backend %[base,map_reg(/var/lib/haproxy/conf/os_http_be.map)]
  use_backend %[req.ssl_sni,lower,map_reg(/var/lib/haproxy/conf/os_tcp_be.map)] if sni sni_passthrough
  use_backend be_sni if sni
  #       use_backend directives below this will be processed.
  use_backend %[base,map_reg(/var/lib/haproxy/conf/os_edge_reencrypt_be.map)]
  #       use_backend directives below this will be processed.
  use_backend %[base,map_reg(/var/lib/haproxy/conf/os_edge_reencrypt_be.map)]

HTTPであれば、このようになっています。
/var/lib/haproxy/conf/os_http_be.map

^wildfly-myproject\.192\.168\.42\.118\.nip\.io(:[0-9]+)?(/.*)?$ be_http:myproject:wildfly
^keycloak-other\.192\.168\.42\.118\.nip\.io(:[0-9]+)?(/.*)?$ be_http:other:keycloak

設定はだいたいわかった感じです。

VM上ではどうなっているんでしょう?OKDが動作しているVMの中に入ってみます。

$ minishift ssh

Routeのコンテナを確認。

$ docker ps | grep router_route
f0299a418978        9bb7abed3e82                                                                                                                     "/usr/bin/openshif..."   About an hour ago   Up About an hour                        k8s_router_router-1-t27rp_default_816e3aaa-3c17-11e9-a1fe-5254006d017f_0

ところで、このVMで80ポートをリッスンしているのは…

$ sudo ss -tnlp | grep 80
LISTEN     0      128          *:80                       *:*                   users:(("haproxy",pid=11251,fd=6))

HAProxyですね…。

$ ps -ef | grep 11251
1001     11251 10437  0 12:42 ?        00:00:00 /usr/sbin/haproxy -f /var/lib/haproxy/conf/haproxy.config -p /var/lib/haproxy/run/haproxy.pid -x /var/lib/haproxy/run/haproxy.sock -sf 197
docker   20087 16753  0 13:02 pts/0    00:00:00 grep --color=auto 11251

どうも、DockerコンテナがVM側から見えているような…?

$ docker exec -it k8s_router_router-1-t27rp_default_816e3aaa-3c17-11e9-a1fe-5254006d017f_0 bash
bash-4.2$ ps -ef
UID        PID  PPID  C STIME TTY          TIME CMD
1001         1     0  0 11:45 ?        00:00:08 /usr/bin/openshift-router
1001       204     1  0 12:42 ?        00:00:00 /usr/sbin/haproxy -f /var/lib/haproxy/conf/haproxy.config -p /var/lib/haproxy/run/haproxy.pid -x /var/lib/haproxy/run/haproxy.sock 
1001       235     0  0 13:03 ?        00:00:00 bash
1001       240   235  0 13:03 ?        00:00:00 ps -ef

VM上でKeycloakのプロセスも見えているので…どうやら、そうっぽいですね。

$ ps -ef | grep keycloak
1000160+  9434  9401  0 12:41 ?        00:00:00 /bin/sh /opt/jboss/keycloak/bin/standalone.sh -Djboss.bind.address=172.17.0.13 -Djboss.bind.address.private=172.17.0.13 -c standalone-ha.xml -b 0.0.0.0
1000160+  9572  9434  3 12:41 ?        00:00:58 /usr/lib/jvm/java/bin/java -D[Standalone] -server -Xms64m -Xmx512m -XX:MetaspaceSize=96M -XX:MaxMetaspaceSize=256m -Djava.net.preferIPv4Stack=true -Djboss.modules.system.pkgs=org.jboss.byteman -Djava.awt.headless=true -Dorg.jboss.boot.log.file=/opt/jboss/keycloak/standalone/log/server.log -Dlogging.configuration=file:/opt/jboss/keycloak/standalone/configuration/logging.properties -jar /opt/jboss/keycloak/jboss-modules.jar -mp /opt/jboss/keycloak/modules org.jboss.as.standalone -Djboss.home.dir=/opt/jboss/keycloak -Djboss.server.base.dir=/opt/jboss/keycloak/standalone -Djboss.bind.address=172.17.0.13 -Djboss.bind.address.private=172.17.0.13 -c standalone-ha.xml -b 0.0.0.0
1000160+  9933  9906  0 12:41 ?        00:00:00 /bin/sh /opt/jboss/keycloak/bin/standalone.sh -Djboss.bind.address=172.17.0.12 -Djboss.bind.address.private=172.17.0.12 -c standalone-ha.xml -b 0.0.0.0
1000160+ 10068  9933  5 12:41 ?        00:01:20 /usr/lib/jvm/java/bin/java -D[Standalone] -server -Xms64m -Xmx512m -XX:MetaspaceSize=96M -XX:MaxMetaspaceSize=256m -Djava.net.preferIPv4Stack=true -Djboss.modules.system.pkgs=org.jboss.byteman -Djava.awt.headless=true -Dorg.jboss.boot.log.file=/opt/jboss/keycloak/standalone/log/server.log -Dlogging.configuration=file:/opt/jboss/keycloak/standalone/configuration/logging.properties -jar /opt/jboss/keycloak/jboss-modules.jar -mp /opt/jboss/keycloak/modules org.jboss.as.standalone -Djboss.home.dir=/opt/jboss/keycloak -Djboss.server.base.dir=/opt/jboss/keycloak/standalone -Djboss.bind.address=172.17.0.12 -Djboss.bind.address.private=172.17.0.12 -c standalone-ha.xml -b 0.0.0.0
1000160+ 10118 10090  0 12:41 ?        00:00:00 /bin/sh /opt/jboss/keycloak/bin/standalone.sh -Djboss.bind.address=172.17.0.14 -Djboss.bind.address.private=172.17.0.14 -c standalone-ha.xml -b 0.0.0.0
1000160+ 10272 10118  5 12:41 ?        00:01:20 /usr/lib/jvm/java/bin/java -D[Standalone] -server -Xms64m -Xmx512m -XX:MetaspaceSize=96M -XX:MaxMetaspaceSize=256m -Djava.net.preferIPv4Stack=true -Djboss.modules.system.pkgs=org.jboss.byteman -Djava.awt.headless=true -Dorg.jboss.boot.log.file=/opt/jboss/keycloak/standalone/log/server.log -Dlogging.configuration=file:/opt/jboss/keycloak/standalone/configuration/logging.properties -jar /opt/jboss/keycloak/jboss-modules.jar -mp /opt/jboss/keycloak/modules org.jboss.as.standalone -Djboss.home.dir=/opt/jboss/keycloak -Djboss.server.base.dir=/opt/jboss/keycloak/standalone -Djboss.bind.address=172.17.0.14 -Djboss.bind.address.private=172.17.0.14 -c standalone-ha.xml -b 0.0.0.0
docker   21605 16753  0 13:06 pts/0    00:00:00 grep --color=auto keycloak

まあ、このあたりは今回はいいかな…。

とりあえず、今回はRouteを構成するHAProxyまわりが確認できたので、よしとしましょう。

AWS Lambdaをaws-sam-cliを使ってローカルで動かす

これは、なにをしたくて書いたもの?

  • AWS Lambdaを、aws-sam-cliを使ってローカルで動かせるらしいので
  • ちょっと試してみようかと

AWS SAM Local(ベータ版) – サーバーレスアプリケーションをローカルに構築してテストする | Amazon Web Services ブログ

aws-sam-localから、今はaws-sam-cliになったみたいです。

以前にLocalStackを使って、ローカルでAWS Lambdaを動かしたことはありましたが、今度はAWSの提供するツールで
行ってみたいと思います。

LocalStackを使って、AWS Lambdaを試してみる - CLOVER🍀

aws-sam-cliのインストール

まずは、aws-sam-cliのインストールを行いましょう。

最初に、Linux用のインストール方法を見たのですが、Linuxbrew…。

Installing the AWS SAM CLI on Linux - AWS Serverless Application Model

他に見ると、pipでインストールする方法もあるようなので、こちらを使うことにしました。

Additional Installation Topics - AWS Serverless Application Model

venvを使って、仮想環境にインストールすることにしました。

$ python3 -m venv venv
$ source venv/bin/activate
$ pip3 install aws-sam-cli

確認。

$ sam --version
SAM CLI, version 0.11.0

これで、aws-sam-cliが使えるようになりました。

なお、aws-sam-cliを使ってローカルでAWS Lambdaを動かす場合、Dockerが必要になるのでインストールしておきましょう。

lambci/lambda

使い方については、GitHubにドキュメントがあるので、こちらを参照。

GitHub - awslabs/aws-sam-cli: AWS SAM CLI 🐿 is a CLI tool for local development and testing of Serverless applications

https://github.com/awslabs/aws-sam-cli/blob/v0.11.0/docs/usage.md

https://github.com/awslabs/aws-sam-cli/blob/v0.11.0/docs/advanced_usage.md

JavaAWS Lambdaを書いてみる

このあたりを見つつ、まずはJavaAWS Lambdaをを使うアプリケーションを書いてみましょう。

環境。

$ java -version
openjdk version "1.8.0_191"
OpenJDK Runtime Environment (build 1.8.0_191-8u191-b12-2ubuntu0.18.04.1-b12)
OpenJDK 64-Bit Server VM (build 25.191-b12, mixed mode)


$ mvn -version
Apache Maven 3.6.0 (97c98ec64a1fdfee7767ce5ffb20918da4f719f3; 2018-10-25T03:41:47+09:00)
Maven home: $HOME/.sdkman/candidates/maven/current
Java version: 1.8.0_191, vendor: Oracle Corporation, runtime: /usr/lib/jvm/java-8-openjdk-amd64/jre
Default locale: ja_JP, platform encoding: UTF-8
OS name: "linux", version: "4.15.0-45-generic", arch: "amd64", family: "unix"

Mavenの設定は、こちらを参考に。

Maven および Eclipse IDE を使用した .jar デプロイパッケージの作成 (Java) - AWS Lambda

Maven依存関係。

        <dependency>
            <groupId>com.amazonaws</groupId>
            <artifactId>aws-lambda-java-core</artifactId>
            <version>1.2.0</version>
        </dependency>

ライブラリ依存関係も含めてひとつのJARファイルにするために、Maven Shade Pluginも適用しておきます。

    <build>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-shade-plugin</artifactId>
                <version>3.2.1</version>
                <executions>
                    <execution>
                        <phase>package</phase>
                        <goals>
                            <goal>shade</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>
        </plugins>
    </build>

実装方法は、以下の2つがあるようです。

ハンドラーの入出力タイプ (Java) - AWS Lambda

ハンドラ作成用に事前定義されているインターフェイスの利用 (Java) - AWS Lambda

今回は、RequestHandlerインターフェースを実装して作成してみましょう。

こんな感じで。
src/main/java/org/littlewings/aws/lambda/MyLambdaFunction.java

package org.littlewings.aws.lambda;

import java.time.LocalDateTime;

import com.amazonaws.services.lambda.runtime.Context;
import com.amazonaws.services.lambda.runtime.RequestHandler;

public class MyLambdaFunction implements RequestHandler<MyLambdaFunction.Request, MyLambdaFunction.Response> {
    @Override
    public Response handleRequest(Request request, Context context) {
        System.out.printf("[%s] request = %s %s%n", LocalDateTime.now(), request.getLastName(), request.getFirstName());

        return new Response("Hello, " + request.getLastName() + " " + request.getFirstName() + "!!");
    }

    public static class Request {
        String firstName;
        String lastName;

        public String getFirstName() {
            return firstName;
        }

        public void setFirstName(String firstName) {
            this.firstName = firstName;
        }

        public String getLastName() {
            return lastName;
        }

        public void setLastName(String lastName) {
            this.lastName = lastName;
        }
    }

    public static class Response {
        String message;

        public Response() {
        }

        public Response(String message) {
            this.message = message;
        }

        public String getMessage() {
            return message;
        }

        public void setMessage(String message) {
            this.message = message;
        }
    }
}

パッケージング。

$ mvn package

aws-sam-cliAWS Lambdaをローカルで動かすには、テンプレートファイルが必要なようです。

今回は、このようなものを作成。 template.yml

AWSTemplateFormatVersion: 2010-09-09
Transform: AWS::Serverless-2016-10-31

Resources:
  MyLambdaJavaFunction:
    Type: AWS::Serverless::Function
    Properties:
      Handler: org.littlewings.aws.lambda.MyLambdaFunction
      CodeUri: ./target/aws-lambda-local-java-example-0.0.1-SNAPSHOT.jar
      Runtime: java8

Resources配下のFunction名は任意の名前です。PropertiesのHandlerには、AWS Lambdaから呼び出される起点となる
クラスを、CodeUriには作成したJARファイルのパスを、Runtimeには実行環境となるDockerイメージのタグを指定します。

使用できる言語のランタイム、バージョンは、GitHubのREADME.mdで確認することができます。

GitHub - awslabs/aws-sam-cli: AWS SAM CLI 🐿 is a CLI tool for local development and testing of Serverless applications

実行はsam local invokeで行います。今回はAWS CLIなしで実行しているので、「--region」でリージョンを指定しています。
リクエストの内容は、標準出力経由でJSONで渡せばOKです。

$ echo '{"firstName": "カツオ", "lastName": "磯野"}' | sam local invoke --region us-west-1

ランタイムのDockerイメージが起動して、AWS Lambdaが動きます。

Fetching lambci/lambda:java8 Docker container image......
2019-03-01 00:03:52 Mounting /tmp/tmp9j3o9vgu as /var/task:ro inside runtime container
START RequestId: dcf625f3-f02d-45bf-8803-e270e282679b Version: $LATEST
END RequestId: dcf625f3-f02d-45bf-8803-e270e282679b
REPORT RequestId: dcf625f3-f02d-45bf-8803-e270e282679b  Duration: 28.98 ms  Billed Duration: 100 ms Memory Size: 128 MB Max Memory Used: 17 MB  
[2019-02-28T15:03:54.057] request = 磯野 カツオ

{"message":"Hello, 磯野 カツオ!!"}

OKですね。

sam local invokeで指定できるオプションは、以下のページや

sam local invoke - AWS Serverless Application Model

ヘルプで確認できます。

$ sam local invoke --help

なお、テンプレートファイルは「--template」で指定することもできますし(デフォルトは「template.yaml」または「template.yml」)、

  -t, --template PATH             AWS SAM template file  [default:
                                  template.[yaml|yml]]

リクエストのJSONの内容をファイルで渡すこともできます。

  -e, --event PATH                JSON file containing event data passed to
                                  the Lambda function during invoke. If this
                                  option is not specified, we will default to
                                  reading JSON from stdin

環境変数を渡したりもできるので、確認してみるとよいでしょう。

特に実行が高速なわけではないですが、ローカルでも動かせるというのはよいですね。

オマケ:Node.js

オマケとして、Node.jsでも動かしてみました。

Node.js の AWS Lambda 関数ハンドラ - AWS Lambda

作成したLambda関数。
lambda.js

exports.myHandler = async (event, context) => {
    console.log(`event = ${JSON.stringify(event)}`);
    console.log(`context = ${JSON.stringify(context)}`);

    return {"message": `Hello ${event.lastName} ${event.firstName}!!`};
}

テンプレートファイル。
template.yml

AWSTemplateFormatVersion: 2010-09-09
Transform: AWS::Serverless-2016-10-31

Resources:
  MyLambdaNodeJsFunction:
    Type: AWS::Serverless::Function
    Properties:
      Handler: lambda.myHandler
      Runtime: nodejs8.10

実行。

$ echo '{"firstName": "カツオ", "lastName": "磯野"}' | sam local invoke --region us-west-1

結果。

Fetching lambci/lambda:nodejs8.10 Docker container image......
2019-03-01 00:12:51 Mounting /path/to as /var/task:ro inside runtime container
START RequestId: 24ca0313-f3fd-110d-7525-c885abc6bdb7 Version: $LATEST
2019-02-28T15:12:54.894Z    24ca0313-f3fd-110d-7525-c885abc6bdb7    event = {"firstName":"カツオ","lastName":"磯野"}
2019-02-28T15:12:54.895Z    24ca0313-f3fd-110d-7525-c885abc6bdb7    context = {"callbackWaitsForEmptyEventLoop":true,"logGroupName":"/aws/lambda/test","logStreamName":"2019/02/28/[$LATEST]776c5662a876fe3374d5bc59b2b82f58","functionName":"test","memoryLimitInMB":"128","functionVersion":"$LATEST","invokeid":"24ca0313-f3fd-110d-7525-c885abc6bdb7","awsRequestId":"24ca0313-f3fd-110d-7525-c885abc6bdb7","invokedFunctionArn":"arn:aws:lambda:us-east-1:426374449862533:function:test"}
END RequestId: 24ca0313-f3fd-110d-7525-c885abc6bdb7
REPORT RequestId: 24ca0313-f3fd-110d-7525-c885abc6bdb7  Duration: 2.33 ms   Billed Duration: 100 ms Memory Size: 128 MB Max Memory Used: 31 MB  

{"message":"Hello 磯野 カツオ!!"}