Skip to content

Instantly share code, notes, and snippets.

@nwiizo
Last active March 13, 2019 17:20
Show Gist options
  • Save nwiizo/7139c2ea73c6f36185fd1342775d2aa2 to your computer and use it in GitHub Desktop.
Save nwiizo/7139c2ea73c6f36185fd1342775d2aa2 to your computer and use it in GitHub Desktop.
minicamp-fukuoka2019
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
name: demo
labels:
app: demo
spec:
replicas: 1
selector:
matchLabels:
app: demo
template:
metadata:
labels:
app: demo
spec:
containers:
- name: demo
image: minicamp_fukuoka:latest
ports:
- containerPort: 80
---
apiVersion: v1
kind: Service
metadata:
name: demo
labels:
app: demo
spec:
ports:
- port: 8080
protocol: TCP
targetPort: 80
nodePort: 30080
selector:
app: demo
type: LoadBalancer
FROM debian:stretch-slim
LABEL maintainer="NGINX Docker Maintainers <docker-maint@nginx.com>"
ENV NGINX_VERSION 1.15.9-1~stretch
ENV NJS_VERSION 1.15.9.0.2.8-1~stretch
RUN set -x \
&& apt-get update \
&& apt-get install --no-install-recommends --no-install-suggests -y gnupg1 apt-transport-https ca-certificates \
&& \
NGINX_GPGKEY=573BFD6B3D8FBC641079A6ABABF5BD827BD9BF62; \
found=''; \
for server in \
ha.pool.sks-keyservers.net \
hkp://keyserver.ubuntu.com:80 \
hkp://p80.pool.sks-keyservers.net:80 \
pgp.mit.edu \
; do \
echo "Fetching GPG key $NGINX_GPGKEY from $server"; \
apt-key adv --keyserver "$server" --keyserver-options timeout=10 --recv-keys "$NGINX_GPGKEY" && found=yes && break; \
done; \
test -z "$found" && echo >&2 "error: failed to fetch GPG key $NGINX_GPGKEY" && exit 1; \
apt-get remove --purge --auto-remove -y gnupg1 && rm -rf /var/lib/apt/lists/* \
&& dpkgArch="$(dpkg --print-architecture)" \
&& nginxPackages=" \
nginx=${NGINX_VERSION} \
nginx-module-xslt=${NGINX_VERSION} \
nginx-module-geoip=${NGINX_VERSION} \
nginx-module-image-filter=${NGINX_VERSION} \
nginx-module-njs=${NJS_VERSION} \
" \
&& case "$dpkgArch" in \
amd64|i386) \
# arches officialy built by upstream
echo "deb https://nginx.org/packages/mainline/debian/ stretch nginx" >> /etc/apt/sources.list.d/nginx.list \
&& apt-get update \
;; \
*) \
# we're on an architecture upstream doesn't officially build for
# let's build binaries from the published source packages
echo "deb-src https://nginx.org/packages/mainline/debian/ stretch nginx" >> /etc/apt/sources.list.d/nginx.list \
\
# new directory for storing sources and .deb files
&& tempDir="$(mktemp -d)" \
&& chmod 777 "$tempDir" \
# (777 to ensure APT's "_apt" user can access it too)
\
# save list of currently-installed packages so build dependencies can be cleanly removed later
&& savedAptMark="$(apt-mark showmanual)" \
\
# build .deb files from upstream's source packages (which are verified by apt-get)
&& apt-get update \
&& apt-get build-dep -y $nginxPackages \
&& ( \
cd "$tempDir" \
&& DEB_BUILD_OPTIONS="nocheck parallel=$(nproc)" \
apt-get source --compile $nginxPackages \
) \
# we don't remove APT lists here because they get re-downloaded and removed later
\
# reset apt-mark's "manual" list so that "purge --auto-remove" will remove all build dependencies
# (which is done after we install the built packages so we don't have to redownload any overlapping dependencies)
&& apt-mark showmanual | xargs apt-mark auto > /dev/null \
&& { [ -z "$savedAptMark" ] || apt-mark manual $savedAptMark; } \
\
# create a temporary local APT repo to install from (so that dependency resolution can be handled by APT, as it should be)
&& ls -lAFh "$tempDir" \
&& ( cd "$tempDir" && dpkg-scanpackages . > Packages ) \
&& grep '^Package: ' "$tempDir/Packages" \
&& echo "deb [ trusted=yes ] file://$tempDir ./" > /etc/apt/sources.list.d/temp.list \
# work around the following APT issue by using "Acquire::GzipIndexes=false" (overriding "/etc/apt/apt.conf.d/docker-gzip-indexes")
# Could not open file /var/lib/apt/lists/partial/_tmp_tmp.ODWljpQfkE_._Packages - open (13: Permission denied)
# ...
# E: Failed to fetch store:/var/lib/apt/lists/partial/_tmp_tmp.ODWljpQfkE_._Packages Could not open file /var/lib/apt/lists/partial/_tmp_tmp.ODWljpQfkE_._Packages - open (13: Permission denied)
&& apt-get -o Acquire::GzipIndexes=false update \
;; \
esac \
\
&& apt-get install --no-install-recommends --no-install-suggests -y \
$nginxPackages \
gettext-base \
&& apt-get remove --purge --auto-remove -y apt-transport-https ca-certificates && rm -rf /var/lib/apt/lists/* /etc/apt/sources.list.d/nginx.list \
\
# if we have leftovers from building, let's purge them (including extra, unnecessary build deps)
&& if [ -n "$tempDir" ]; then \
apt-get purge -y --auto-remove \
&& rm -rf "$tempDir" /etc/apt/sources.list.d/temp.list; \
fi
# forward request and error logs to docker log collector
RUN ln -sf /dev/stdout /var/log/nginx/access.log \
&& ln -sf /dev/stderr /var/log/nginx/error.log
EXPOSE 80
STOPSIGNAL SIGTERM
CMD ["nginx", "-g", "daemon off;"]
package main
import (
"fmt"
"log"
"net/http"
)
func handler(w http.ResponseWriter, r *http.Request) {
fmt.Fprintln(w, "Hello, 世界")
}
func main() {
http.HandleFunc("/", handler)
log.Fatal(http.ListenAndServe(":80", nil))
}

セキュリティ・ミニキャンプ in 福岡 2019 Private CaaS 基盤の構築と開発 演習

Webのインフラシステムを取り巻く環境は多様性の名の下に混沌を極めています。また、DockerやKubernetesをはじめとしたコンテナ技術の台頭は人々をクラウドネイティブコンピューティングという更なる混沌へと導きました。本講義では、Infrastructure as a Service な環境上にKubernetes as a Service、Function as a Serviceの構築を行い、実際に簡単なアプリケーションの開発を通してクラウドネイティブなインフラや開発について学んでもらいたいと思います。

1. ConoHaの登録と VMの準備

  • アカウントの登録
  • 推奨OS Ubuntu 18.04 LTS (検証これでやった)
  • 推奨VMサイズ 4GB以上 (みんなもっと盛って遊んでいいよ)

2. OSの基本設定とAnsibleのインストール

パッケージのダウンロード

# apt-get update
# apt-get install software-properties-common
# apt-add-repository --yes --update ppa:ansible/ansible
# apt-get install ansible

今回はk8sやDockerに触れるファーストなので全部サクッとAnsibleで構築してしまいます

# git clone https://github.com/nwiizo/minicamp-fukuoka2019

待てばなおりますがapt がどうしても終わらない人

# ps aux |grep apt
# kill -9 <PID>

3. Ansibleの実行

Ansibleの実行を行います.ここで詰まったら一緒に泣きながらデバッグしましょうDocument vim /etc/ansible/ansible.cfg

[defaults]
host_key_checking = False

vim hosts.yml

[openfaas:children]
OpenFaaS

[OpenFaaS]
<ex-IP>

コマンドの実行

# ansible-playbook -i ./hosts.yml ./site.yml -l "<ex-IP>" -k

4.確認(手動)

インフラを自動で管理する方法はいくつかあって有名なものでいうとserverspecGossなどのツールがあります.

Ansibleの最後に出てくるこの出力は保存しておきましょう.

TASK [output : Echo deployment details] *****************************************************************************
ok: [*.*.*.*] => {
    "msg": [
        "apiVersion: *******,
        "OpenFaaS Gateway: http://*.*.*.*:31112",
        "Gateway User: admin",
        "Gateway Password: 3ac717368db266f1d60152e870bb1f40eac2d24a",
        "CLI Gateway Login: echo -n ******** | faas-cli login --username=admin --password-stdin -g http://*.*.*.*:31112"
    ]
}

  • Dockerの確認
# docker -v
  • Kubernetesの確認
# su - openfaas
# bashrcにでも入れとけばいい
# export KUBECONFIG=/home/openfaas/.kube/config
# cluster の確認
# kubectl version
Client Version: version.Info{Major:"1", Minor:"13", GitVersion:"v1.13.4", GitCommit:"c27b913fddd1a6c480c229191a087698aa92f0b1", GitTreeState:"clean", BuildDate:"2019-02-28T13:37:52Z", GoVersion:"go1.11.5", Compiler:"gc", Platform:"linux/amd64"}
Server Version: version.Info{Major:"1", Minor:"13", GitVersion:"v1.13.4", GitCommit:"c27b913fddd1a6c480c229191a087698aa92f0b1", GitTreeState:"clean", BuildDate:"2019-02-28T13:30:26Z", GoVersion:"go1.11.5", Compiler:"gc", Platform:"linux/amd64"}

クラスターの詳細情報

# kubectl cluster-info
Kubernetes master is running at https://*.*.*.*:6443
KubeDNS is running at https://*.*.*.*:6443/api/v1/namespaces/kube-system/services/kube-dns:dns/proxy

nodeの確認

# kubectl get nodes
NAME             STATUS   ROLES    AGE   VERSION
*-*-*-*          Ready    master   16m   v1.13.4

Namespaceの確認

# kubectl get namespaces
NAME          STATUS   AGE
default       Active   22m
kube-public   Active   22m
kube-system   Active   22m
openfaas      Active   21m
openfaas-fn   Active   21m

Podの確認

# kubectl get pods --all-namespaces
NAMESPACE     NAME                                     READY   STATUS    RESTARTS   AGE
kube-system   coredns-86c58d9df4-d45kz                 1/1     Running   0          26m
kube-system   coredns-86c58d9df4-xt7lk                 1/1     Running   0          26m
kube-system   etcd-150-95-147-209                      1/1     Running   0          25m
kube-system   kube-apiserver-150-95-147-209            1/1     Running   0          25m
kube-system   kube-controller-manager-150-95-147-209   1/1     Running   0          25m
kube-system   kube-proxy-5k79s                         1/1     Running   0          26m
kube-system   kube-scheduler-150-95-147-209            1/1     Running   0          25m
kube-system   tiller-deploy-5b7c66d59c-p5gdc           1/1     Running   0          26m
kube-system   weave-net-rcpkr                          2/2     Running   0          26m
openfaas      alertmanager-76559bd64c-8swvk            1/1     Running   0          25m
openfaas      faas-idler-7945c9bc7b-8n4vh              1/1     Running   1          25m
openfaas      gateway-7b7455dfd8-hbld9                 2/2     Running   1          25m
openfaas      nats-6686bb4b95-56hbj                    1/1     Running   0          25m
openfaas      prometheus-79d9fcf57b-8qlgg              1/1     Running   0          25m
openfaas      queue-worker-8655bb54cb-pr4nh            1/1     Running   1          25m

5. Docker の実行

ないなら良いが# docker loginをやっとくと今後は楽.こちらの演習はrootユーザーで実行してください.

  • とりあえず,Hello world
# docker run hello-world
Unable to find image 'hello-world:latest' locally
latest: Pulling from library/hello-world
1b930d010525: Pull complete
Digest: sha256:2557e3c07ed1e38f26e389462d03ed943586f744621577a99efb77324b0fe535
Status: Downloaded newer image for hello-world:latest

Hello from Docker!

確認しました.

# docker images | grep hello
hello-world                          latest              fce289e99eb9        8 weeks ago         1.84kB
  • Nginxの公開
# docker pull docker.io/nginx
# docker run -d -p 8000:80 --name nginx-latest docker.io/nginx:latest
# wget 127.0.0.1:8000

ブラウザで確認後 Docker の削除

# docker ps | grep nginx
9fd4701f4953        nginx:latest                    "nginx -g 'daemon of…"   About a minute ago   Up About a minute   0.0.0.0:80->80/tcp   nginx-latest
# docker stop 9fd4701f4953
9fd4701f4953
# docker ps | grep nginx
  • DockerFileでのデプロイ
# Gist上のコピペしてください.DockerFileを書いて
# vim Dockerfile
# build して
# docker build . -t minicamp_fukuoka
# docker images | grep minicamp
minicamp_fukuoka                     latest              ecb3f44aea9f        2 minutes ago       109MB 
# 走らせませす.
# docker run -d -p 8080:80 --name minicamp_fukuoka minicamp_fukuoka:latest

ブラウザで確認してください アクセスできませんでしかた?残念… Docker -p とかでoption について調べてみましょう‼ 終わったらちゃんと削除してくださいね

# docker ps | grep minicamp
# docker kill <CONTAINER ID>

※チャレンジ課題:同様にDockerFileからApacheをビルドしてみてください.

6. Kubernetes の実行

ないなら良いが# docker loginをやっとくと今後は楽.OpenFaaSユーザーで実行してください

vim demo.yaml
# kubectl apply -f demo.yaml
# kubectl get pods --selector app=demo
# kubectl get service
NAME         TYPE           CLUSTER-IP     EXTERNAL-IP   PORT(S)          AGE
demo         LoadBalancer   10.108.16.22   <pending>     8080:30080/TCP   3m41s
kubernetes   ClusterIP      10.96.0.1      <none>        443/TCP          108m

削除します

# kubectl delete -f demo.yaml
deployment.extensions "demo" deleted
service "demo" deleted

※チャレンジ課題:同様にApacheで動作するPodを動作させてください.

7. OpenFaaS の実行

  • OpenFaaSの確認 ないなら良いが# docker loginをやっとくと今後は楽.rootユーザーで実行してください
  • faas-cliのインストール
# curl -sL cli.openfaas.com | sh
x86_64
Downloading package https://github.com/openfaas/faas-cli/releases/download/0.8.3/faas-cli as /tmp/faas-cli
Download complete.

Running as root - Attempting to move faas-cli to /usr/local/bin
New version of faas-cli installed to /usr/local/bin
Creating alias 'faas' for 'faas-cli'.
  ___                   _____           ____
 / _ \ _ __   ___ _ __ |  ___|_ _  __ _/ ___|
| | | | '_ \ / _ \ '_ \| |_ / _` |/ _` \___ \
| |_| | |_) |  __/ | | |  _| (_| | (_| |___) |
 \___/| .__/ \___|_| |_|_|  \__,_|\__,_|____/
      |_|

CLI:
 commit:  a141dedf94ffeed84412365fd591bdc8999c5a1b
 version: 0.8.3
  • ログイン
# echo -n <password> | faas-cli login --username=admin --password-stdin -g http://*.*.*.*:31112
Calling the OpenFaaS server to validate the credentials...
WARNING! Communication is not secure, please consider using HTTPS. Letsencrypt.org offers free SSL/TLS certificates.
credentials saved for admin http://*.*.*.*:31112
  • Grafana
kubectl -n openfaas run \
--image=stefanprodan/faas-grafana:4.6.3 \
--port=3000 \
grafana
  • functionのデプロイ準備
 # mkdir -p workspace \
   && cd workspace
# faas-cli template pull
# 利用できる言語の確認
# faas-cli new --list
Languages available as templates:
- csharp
- csharp-armhf
- dockerfile
- go
- go-armhf
- java8
- node
- node-arm64
- node-armhf
- php7
- python
- python-armhf
- python3
- python3-armhf
- ruby
  • Function 作成
# faas-cli new --lang go hello-openfaas
  • directory
./hello-openfaas.yml
./hello-openfaas
./hello-openfaas/handler.go
  • deploy vim ./hello-openfaas.yml
provider:
  name: faas
  gateway: http://<ex-IP>:<Openfaas-port>
functions:
  hello-openfaas:
    lang: go
    handler: ./hello-openfaas
    image: <docker-id>/hello-openfaas:latest
# faas-cli build -f ./hello-openfaas.yml
# faas-cli push -f ./hello-openfaas.yml
# faas-cli deploy -f ./hello-openfaas.yml

※チャレンジ課題:main.goをDockerおよびKubernetesで動作させて外部接続を確保してください.

  • 確認 http://<ex-ip>:31112 で外部からログイン及び確認をお願いします.

これで準備していた演習は全て終了です.この後は用意した環境で下記のコンテンツで遊ぶか 話してる無駄話を聞いてもらってもどっちでもかまいません.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment