KafkaをローカルのDocker環境で、さくっと動かしてみました 　第１回


## 概要
Kafkaに魅せられて、とりあえず手元のマシンで動かしてみましょうか、、、と、インフラしか知らないSEがMacBookProを新たに購入し、Qiita等にアップされている諸先輩方の記事を参考にさせていただき、動作確認したまでの手順を７回に分け記載しています。
なお、Kafkaの概要につきましたは、[こちらの記事](https://qiita.com/sigmalist/items/5a26ab519cbdf1e07af3) を参照ください。

今回の目指すべく Kafka の全体構成は下図のようになります。
![kafka-00.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/544022/a98ea391-27e1-38b7-5b6f-141032ea92e5.png)


これを目指し、第１回は zookeeper と broker と Producer/Comsumer を稼働させるための cli をDockerコンテナで稼働させてみます。
![kafka-1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/544022/351da61f-9ec2-efb6-bc18-71247fc022c5.png)
なお、Dockerについては[この書籍](https://gihyo.jp/book/2020/978-4-297-11428-2)を参考にさせていただきました。


## 実行環境
macOS Big Sur 11.1 
Docker version 20.10.2, build 2291f61
Python 3.8.3

## ネットワークの定義
まずは、本件のために使用するネットワークを定義します。
もちろん全コンテナは１セグメントで稼働させます。

```
$ docker network create iot_network
7a00a485b89f83d664fef537f21e7df16ba34f14dc2731bc8686d2b0c55c1fe3
```

## docker-composeファイル
zookeeper と broker と cli コンテナを定義した docker-compose.yml は以下となります。
使用するネットワーク（上記で作成したもの）も定義しています。

```docker-compose.yml

version: "3"
services:
  zookeeper:
    image: confluentinc/cp-zookeeper:5.5.1
    hostname: zookeeper
    container_name: zookeeper
    ports:
      - "32181:32181"
    environment:
      ZOOKEEPER_CLIENT_PORT: 32181
      ZOOKEEPER_TICK_TIME: 2000

  broker:
    image: confluentinc/cp-kafka:5.5.1
    hostname: broker
    container_name: broker
    depends_on:
      - zookeeper
    ports:
      - "9092:9092"
      - "29092:29092"
    environment:
      KAFKA_BROKER_ID: 1
      KAFKA_ZOOKEEPER_CONNECT: "zookeeper:32181"
      KAFKA_LISTENER_SECURITY_PROTOCOL_MAP: PLAINTEXT:PLAINTEXT,PLAINTEXT_HOST:PLAINTEXT
      KAFKA_ADVERTISED_LISTENERS: PLAINTEXT://broker:29092,PLAINTEXT_HOST://localhost:9092
      KAFKA_OFFSETS_TOPIC_REPLICATION_FACTOR: 1
      CONFLUENT_SUPPORT_METRICS_ENABLE: "false"

  cli:
    image: confluentinc/cp-kafka:5.5.1
    hostname: cli
    container_name: cli
    depends_on:
      - broker
    entrypoint: /bin/sh
    tty: true

networks:
  default:
    external:
      name: iot_network
```

## コンテナの作成と確認
定義したコンテナをビルドして起動させます。

```
$ docker-compose up -d
    前略
Creating zookeeper ... done
Creating broker    ... done
Creating cli       ... done
```

起動しているコンテナを確認します。

```
$ docker-compose ps
   Name                Command            State               Ports                         
----------------------------------------------------------------------------------------------------------
broker      /etc/confluent/docker/run   Up          0.0.0.0:29092->29092/tcp, 0.0.0.0:9092->9092/tcp      
cli         /bin/sh                     Up          9092/tcp                                              
zookeeper   /etc/confluent/docker/run   Up          2181/tcp, 2888/tcp, 0.0.0.0:32181->32181/tcp, 3888/tcp
```

## ネットワーク情報の確認
各コンテナにアサインされたネットワーク情報についても確認します。
各コンテナ間の通信はコンテナ名で実施されるため、IPアドレスを意識する必要はありません。

```
$ docker network inspect iot_network

[
    {
        "Name": "iot_network",
        "Id": "7a00a485b89f83d664fef537f21e7df16ba34f14dc2731bc8686d2b0c55c1fe3",
        "Created": "2021-02-03T15:58:22.6410234Z",
        "Scope": "local",
        "Driver": "bridge",
        "EnableIPv6": false,
        "IPAM": {
            "Driver": "default",
            "Options": {},
            "Config": [
                {
                    "Subnet": "172.21.0.0/16",
                    "Gateway": "172.21.0.1"
                }
            ]
        },
        "Internal": false,
        "Attachable": false,
        "Ingress": false,
        "ConfigFrom": {
            "Network": ""
        },
        "ConfigOnly": false,
        "Containers": {
            "192c2091a0cbad678edfd6165b8392be9e6e17b7b4eb74179303c366d6efa301": {
                "Name": "broker",
                "EndpointID": "ace1688ef02c686264325019143afef994078e53501586ebf7859c4a5b8b4ef9",
                "MacAddress": "02:42:ac:15:00:03",
                "IPv4Address": "172.21.0.3/16",
                "IPv6Address": ""
            },
            "79634a9c332300d558235170e19f9ede4528d4566c95eceaf0adc31b1ab9e441": {
                "Name": "zookeeper",
                "EndpointID": "fcdcd02386f9f972d6a93e8d7b2820f3df8039f0749ff2c9981ca3e7754322f0",
                "MacAddress": "02:42:ac:15:00:02",
                "IPv4Address": "172.21.0.2/16",
                "IPv6Address": ""
            },
            "dd58a95c5904c456e728e9fd881b50e89b1138a23424378cedde87d86c95bba0": {
                "Name": "cli",
                "EndpointID": "690e00daf32594623a0068a86fbbe5be90a53f42f1901606d59f035ff6c43b1c",
                "MacAddress": "02:42:ac:15:00:04",
                "IPv4Address": "172.21.0.4/16",
                "IPv6Address": ""
            }
        },
        "Options": {},
        "Labels": {}
    }
]
```

これで、Kafka基本コンポーネントをローカルのDocker環境で稼働させることを確認しました。


## 次回について
次回（第２回）は Producerからメッセージを送り、Consumerでそのメッセージの受け取りを確認します。

[第１回：Kafka基本コンポーネントをローカルのDocker環境で稼働させる](https://qiita.com/turupon/items/12268ddb95ecd7b7ae07)
[第２回：Kafkaの Producerから送信されたメッセージが Broker を経由して Consumer で受け取れることの確認](//qiita.com/turupon/items/59eb602766a38bc3b621)
[第３回：Producer上のPythonプログラムで生成したデータを Broker を経由して Consumer で受け取れることの確認](https://qiita.com/turupon/items/60ac1ec68fe8148b9201)
[第４回：Producer上での生成データが topic-01 を経由して KSQL（topic01_stream１ → topic01_stream2） でストリーミング抽出処理されたことの確認](https://qiita.com/turupon/items/540be949ead3f4065553)
[第５回：Producer上での生成データが topic-01 → Ksql → topic-11 を経由して Consumer 上のPythonプログラムで受け取れることの確認](https://qiita.com/turupon/items/bd27834a42dda865469d)
[第６回：Producer上での生成データが topic-01 → Ksql → topic-11 を経由して Consumer 上のPythonプログラムによってS3に書き込めることの確認](https://qiita.com/turupon/items/5714c2cd45badd08f00b)
[第７回：２つのProducerコンテナ上で生成したそれぞれのデータが topic-01 → Ksql → topic-11 を経由して Consumer 上のPythonプログラムで受け取れることの確認](https://qiita.com/turupon/items/7f50d7b453a02989b88c)


## 参考情報
以下の情報を参考にさせていただきました。感謝申し上げます。
[Kafka の Docker のチュートリアル](https://qiita.com/psyashes/items/e50bdfe35a2e7778986d)
[Kafka からKSQLまで　Dockerで簡単環境構築](https://qiita.com/dublog/items/4b7f0d41a4075f794bd8)