<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
    <channel>
        <title>Dev-Hi.log</title>
        <link>https://velog.io/</link>
        <description></description>
        <lastBuildDate>Sat, 08 Apr 2023 13:56:53 GMT</lastBuildDate>
        <docs>https://validator.w3.org/feed/docs/rss2.html</docs>
        <generator>https://github.com/jpmonette/feed</generator>
        <image>
            <title>Dev-Hi.log</title>
            <url>https://images.velog.io/images/star-whale/profile/6d18b967-602e-43d4-ad11-b0a4da111e13/Closed_Circle.png</url>
            <link>https://velog.io/</link>
        </image>
        <copyright>Copyright (C) 2019. Dev-Hi.log. All rights reserved.</copyright>
        <atom:link href="https://v2.velog.io/rss/star-whale" rel="self" type="application/rss+xml"/>
        <item>
            <title><![CDATA[minikube에서 docker registry 설치하기(m1 mac)]]></title>
            <link>https://velog.io/@star-whale/minikube%EC%97%90%EC%84%9C-docker-registry-%EC%84%A4%EC%B9%98%ED%95%98%EA%B8%B0m1-mac</link>
            <guid>https://velog.io/@star-whale/minikube%EC%97%90%EC%84%9C-docker-registry-%EC%84%A4%EC%B9%98%ED%95%98%EA%B8%B0m1-mac</guid>
            <pubDate>Sat, 08 Apr 2023 13:56:53 GMT</pubDate>
            <description><![CDATA[<h2 id="개발-환경">개발 환경</h2>
<ul>
<li>mac os</li>
<li>apple silicon(m1)</li>
<li>docker desktop</li>
<li>minikube</li>
<li>curl 명령어</li>
<li>kubectl</li>
</ul>
<h2 id="1-실행가이드">1. 실행가이드</h2>
<h3 id="11-minikube-실행">1.1 minikube 실행</h3>
<p>다음의 명령어를 통해 kubernetes를 기존 docker runtime으로 설치한다.</p>
<pre><code class="language-shell">minikube start --driver=docker</code></pre>
<h3 id="12-private-docker-registry-활성화">1.2 private docker registry 활성화</h3>
<pre><code class="language-shell">minikube addons enable registry</code></pre>
<p>위의 명령어를 입력하면 registry가 사용하는 port번호가 다음과 같이 나온다는 것을 확인할 수 있다.
<img src="https://velog.velcdn.com/images/star-whale/post/d733704d-5b63-48fd-8b4d-fa01e000713a/image.png" alt=""></p>
<p>사용자(<code>본인</code>)가 tls 인증서 없이, image pull을 할 수 있도록 설정한다.</p>
<pre><code class="language-shell">minikube config set insecure-registry &quot;10.0.0.0/24&quot;</code></pre>
<p>curl 명령어를 통해, registry에 접속할 수 있는지 확인하자.</p>
<pre><code class="language-shell">curl http://localhost:49802/v2/_catalog # 49802 대신, 터미널에 출력된 port번호 입력</code></pre>
<p><img src="https://velog.velcdn.com/images/star-whale/post/0d0f077a-fc26-44ce-9deb-cf45217745d4/image.png" alt=""></p>
<p>저장한 image가 존재하지 않기 때문에, 위와 같이 <code>repositories</code>의 값이 <code>[]</code>인 것을 확인할 수 있다.</p>
<p>위의 명령어에서 ip주소가 <code>10.0.0.0/24</code>인 이유는 아래의 <a href="https://minikube.sigs.k8s.io/docs/handbook/registry/#enabling-insecure-registries">공식문서</a> 일부 참고.</p>
<blockquote>
<p>Because the default service cluster IP is known to be available at 10.0.0.1, users can pull images from registries deployed inside the cluster by creating the cluster with minikube start --insecure-registry &quot;10.0.0.0/24&quot;.</p>
</blockquote>
<br/>

<h2 id="2-docker-registry-test">2. docker registry test</h2>
<h4 id="테스트에-사용된-도구">테스트에 사용된 도구</h4>
<ul>
<li>intellij</li>
<li>jib</li>
<li>jdk1.8</li>
<li>kubectl</li>
<li>chrome</li>
<li>curl</li>
</ul>
<p>다음의 절차로 docker registry를 test한다.</p>
<ol>
<li>Push image of spring app to the registry</li>
<li>Check existence of the image in the registry</li>
<li>Deploy the image to kubernetes</li>
</ol>
<p>이전에 window에서 동일한 작업을 했던 <a href="https://velog.io/@star-whale/minikube%EC%97%90%EC%84%9C-private-docker-registry-%EC%84%A4%EC%B9%98-%EB%B0%8F-%ED%99%9C%EC%9A%A9%ED%95%98%EA%B8%B0">minikube에서 private docker registry 설치 및 활용하기</a>에서 사용한 spring app을 사용하자</p>
<h3 id="21-push-image-of-spring-app-to-the-registry">2.1 Push image of spring app to the registry</h3>
<p><code>build.gradle</code>의 <code>jib.to.image</code>에서 port번호 변경</p>
<pre><code class="language-gradle">
plugins {
    id &#39;org.springframework.boot&#39; version &#39;2.7.3&#39;
    id &#39;io.spring.dependency-management&#39; version &#39;1.0.13.RELEASE&#39;
    id &#39;java&#39;
    id &#39;com.google.cloud.tools.jib&#39; version &#39;3.3.1&#39; // add the plugin if not exist
}


jib {
    to {
        image = &quot;localhost:49802/example&quot; 
    }

    // local docker registry를 사용하기 때문에, http 허용
    allowInsecureRegistries true
}</code></pre>
<p>gradlew가 있는 경로에서 다음의 명령어를 통해, spring app 빌드부터 image push까지 진행한다.</p>
<pre><code class="language-shell">./gradlew jib</code></pre>
<h3 id="22-check-existence-of-the-image-in-the-registry">2.2 Check existence of the image in the registry</h3>
<p>이전에 입력했던 curl 명령어를 다시 한번 입력해서, image가 registry에 올라갔는지 확인하자.</p>
<pre><code class="language-shell">curl http://localhost:49802/v2/_catalog # 49802 대신, 터미널에 출력된 port번호 입력</code></pre>
<p>결과는 다음과 같다.</p>
<p><img src="https://velog.velcdn.com/images/star-whale/post/b56b7e3f-6b23-4c16-9aad-4f328d401649/image.png" alt=""></p>
<h3 id="23-deploy-the-image-to-kubernetes">2.3 Deploy the image to Kubernetes</h3>
<p>이전 글에서 사용됐던 <code>deployment.yaml</code>를 사용하자. 이를 위해서는 image가 들어있는 registry에 대한 cluster ip주소를 알아야한다. 다음의 명령어를 통해 ip주소를 알 수 있다.</p>
<pre><code class="language-shell">kubectl get svc -n kube-system</code></pre>
<p><code>NAME</code>이 <code>registry</code>인 부분의 <code>CLUSTER-IP</code>를 확인하면된다. </p>
<p>이전에 사용했던 <code>deployment.yaml</code>의 <code>spec.containers[].image</code> 값에 반영하면된다.
작성자의 경우 window와 달리 mac에서는 pod에서 <code>OOMKilled</code>가 발생하여 <code>resource.limit.memory</code> 값을 <code>512Mi</code>로 늘렸다. </p>
<pre><code class="language-yaml">apiVersion: apps/v1
kind: Deployment
metadata:
  name: myapp
spec:
  selector:
    matchLabels:
      app: myapp
  template:
    metadata:
      labels:
        app: myapp
    spec:
      containers:
        - name: myapp
          image: 10.97.23.247/example
          imagePullPolicy: IfNotPresent
          resources:
            limits:
              memory: &quot;512Mi&quot;
              cpu: &quot;500m&quot;
          ports:
            - containerPort: 8080

---
apiVersion: v1
kind: Service
metadata:
  name: myapp-svc
spec:
  type: NodePort
  selector:
    app: myapp
  ports:
    - port: 80
      targetPort: 8080
      nodePort: 31212</code></pre>
<p>아래의 명령어를 이용하여, service, deployment를 kubernetes에 적용하자.</p>
<pre><code class="language-shell">kubectl apply -f example-app-deployment.yaml</code></pre>
<p><code>kubectl get pods</code>를 입력하여 spring app이 정상적으로 deploy 됐는지 확인하자.</p>
<p><img src="https://velog.velcdn.com/images/star-whale/post/1db1b263-091c-45eb-ba26-dda869ac6758/image.png" alt=""></p>
<p>이번에는 local port(브라우저에서 입력할 port번호)에서 service port로 forwarding하는 방식을 사용하자.</p>
<p>우선 위의 <code>deployment.yaml</code>에 존재하는 <code>service</code>에 따르면 port번호 80으로 traffic이 들어오면 이 요청을 port번호 8080으로 forwarding 하는 것을 알 수 있다. kubernetes 내에서 이 service의 port를 드러낸다.</p>
<p>한편, kubernetes 외부에 있는 우리의 브라우저(e.g. 크롬)는 우리가 정한 port에서 service port로 forwarding해서 사용하면된다. 아래의 명령어를 통해 이를 진행하자.</p>
<pre><code class="language-shell">sudo kubectl port-forward service/myapp-svc 23456:80</code></pre>
<p>위의 명령어에 의해, local port번호 23456(임의로 정한 번호) -&gt; service port번호 80으로 forwarding 되고,
우리가 정의한 service에 의해, service port번호 80 -&gt; container port번호 8080으로 forwarding 된다. 명령어의 결과는 다음과 같다.</p>
<p><img src="https://velog.velcdn.com/images/star-whale/post/694cd033-09bb-40e7-885f-b8b526d52094/image.png" alt=""></p>
<p>이제 브라우저에서 요청을 하자. <code>localhost:23456/ping</code>을 브라우저에서 입력하면 화면에 <code>pong</code>이라는 글자가 나오는 것을 확인할 수 있다.</p>
<h2 id="3-참고사항2022-04-08-기준">3. 참고사항(2022-04-08 기준)</h2>
<p>registry container에서 image를 영속화하기 위한 volume이 없다. registry deployment의 volume 부분을 확인하고, <code>k9s</code>에서 pvc도 확인했는데 관련된 부분은 존재하지 않았다. 실제로 테스트도 진행했는데, <code>./gradlew jib</code>를 이용하여 spring app image를 registry에 push 한 후, registry container를 재실행 후, curl로 확인하면 저장된 image가 존재하지 않는다는 것을 확인했다.</p>
<p><code>./gradlew jib</code> 이후, curl로 다음의 결과를 확인한 후,
<img src="https://velog.velcdn.com/images/star-whale/post/c08bd8fb-14cd-49bd-bf6a-7650fa75ea59/image.png" alt=""></p>
<p>k9s를 이용하여 registry container를 재실행을 했다.</p>
<p><img src="https://velog.velcdn.com/images/star-whale/post/737c9cbf-e700-4c2b-b286-84fdad8c1b3f/image.png" alt=""></p>
<p>이후 다시 curl로 다시 확인하면,
<img src="https://velog.velcdn.com/images/star-whale/post/e01d8206-df91-4941-857b-1e230bb13f2b/image.png" alt=""></p>
<p>이전에 올렸던 image가 존재하지 않은 것을 확인할 수 있다.</p>
<p>그리고 minikube는 docker container위에서 실행된다. 따라서 컴퓨터를 재부팅할 때, minikube도 다시 시작해야하는데, 문제는 시작할 때마다, registry의 port가 변경된다. 따라서, <code>build.gradle</code>에서 <code>jib.image.to</code>에서 registry port를 계속 변경해야하므로 번거롭다.</p>
<p>minikube에서 제공하는 registry를 사용하는 대신, registry에 대한 deployment와 service를 다음에 직접 작성해야겠다.</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[minikube에서 private docker registry 설치 및 활용하기]]></title>
            <link>https://velog.io/@star-whale/minikube%EC%97%90%EC%84%9C-private-docker-registry-%EC%84%A4%EC%B9%98-%EB%B0%8F-%ED%99%9C%EC%9A%A9%ED%95%98%EA%B8%B0</link>
            <guid>https://velog.io/@star-whale/minikube%EC%97%90%EC%84%9C-private-docker-registry-%EC%84%A4%EC%B9%98-%EB%B0%8F-%ED%99%9C%EC%9A%A9%ED%95%98%EA%B8%B0</guid>
            <pubDate>Tue, 24 Jan 2023 08:09:38 GMT</pubDate>
            <description><![CDATA[<h2 id="1-minikube에-private-docker-registry를-설치하게된-이유">1. minikube에 private docker registry를 설치하게된 이유</h2>
<p>local에서 minikube를 이용하여 k8s기반 spring app을 개발하면서, deploy를 위해 spring app에 대한 docker image를 docker hub에 push 하는 것이 마음에 들지 않았다. <strong>모든 것을 local에서 처리하고 싶었기 때문이다.</strong> 그래서 docker hub 대신, private registry를 minikube위에 만들고, 해당 resgitry에 있는 image를 동일한 minikube에 deploy 하기로 결심했다.
<br/></p>
<h2 id="2-설치-가이드">2. 설치 가이드</h2>
<h3 id="21-개발-환경">2.1 개발 환경</h3>
<p>설치 가이드를 안내하기 전에, 작성자가 사용한 개발환경은 다음과 같다.</p>
<ul>
<li>minikube v1.28.0</li>
<li>Window10</li>
<li>wsl2(ubuntu 22.04.1 LTS)</li>
<li>kubectl v1.25.3</li>
<li>docker desktop</li>
</ul>
<br/>
참고로 docker desktop은 window10에서 설치됐고, 그 외 나머지는 wsl2에 설치됐다.

<h3 id="22-minikube에-private-registry-설치">2.2 minikube에 private registry 설치</h3>
<p>다음의 명령어를 입력해서 minikube에 private registry를 활성화하자.(minikube가 실행되고 있어야함)</p>
<pre><code class="language-shell">minikube addons enable registry</code></pre>
<br/>
위의 명령어를 나오면 private registry에서 사용하는 포트번호를 알려주는데, minikube에 spring app을 deploy할 때, 해당 포트번호를 사용해야하므로 기억해야한다.

<blockquote>
<p>Registry addon with docker driver uses port 49955 please use that instead of default port 5000</p>
</blockquote>
<p>작성자의 경우에는 사용할 포트번호로 49955가 나왔다. 앞으로 이 포트번호를 이용하여 가이드를 작성할 예정이다.</p>
<p>client가 http를 통해 image를 pull할 수 있도록 설정한다. service cluster ip는 <code>10.0.0.1</code>에서 사용가능하기 때문에, 이 범주에 있는 ip주소는 http를 사용할 수 있도록 설정한다.(<a href="https://minikube.sigs.k8s.io/docs/handbook/registry/#enabling-insecure-registries">https://minikube.sigs.k8s.io/docs/handbook/registry/#enabling-insecure-registries</a> 참고)</p>
<pre><code class="language-shell">minikube config set insecure-registry &quot;10.0.0.0/24&quot;</code></pre>
<br/>
wsl2에서 curl 명령어를 이용하여 private registry가 정상적으로 설치됐는지 확인하자.

<pre><code class="language-shell">curl http://localhost:49955/v2/_catalog </code></pre>
<br/>
결과는 다음과 같다.

<pre><code class="language-js">{&quot;repositories&quot;:[]}</code></pre>
<br/>
이번에는 kubectl 명령어를 이용하여 확인하자. 

<pre><code>kubectl get service --namespace kube-system</code></pre><p>작성자의 경우 다음의 결과를 얻었다.</p>
<pre><code>NAME       TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)                  AGE
kube-dns   ClusterIP   10.96.0.10      &lt;none&gt;        53/UDP,53/TCP,9153/TCP   33m
registry   ClusterIP   10.102.107.53   &lt;none&gt;        80/TCP,443/TCP           30m</code></pre><p>registry가 minikube 위에서 활성화 되면, registry addon은 minikube의 가상 머신 위에서 포트번호 80을 expose한다는 것을 확인할 수 있다.</p>
<br/>
minikube 위에 private registry를 설치하는 것은 완료되었다. addon이 있어서 private registry 설치하는 과정은 어렵지 않다.


<h2 id="3-spring-app-build-image-build-pushing-image-to-registry">3. Spring app build, image build, pushing image to registry</h2>
<h3 id="31-개발환경">3.1 개발환경</h3>
<p>spring app에 사용된 개발환경은 다음과 같다.</p>
<ul>
<li>spring boot 2.7.3</li>
<li>jdk8</li>
<li>gradle</li>
<li>jib</li>
<li>intellij<br/>

</li>
</ul>
<p>참고로 테스트에 사용한 spring app은 <a href="https://github.com/Dev-Hi/minikube-docker-registry-test">https://github.com/Dev-Hi/minikube-docker-registry-test</a> 에서 확인할 수 있으며, 아주 간단한 spring app이다. 참고로 작성자의 경우 spring app의 프로젝트 경로는 wsl2상에 존재한다.</p>
<h3 id="32-jib">3.2 jib</h3>
<p>jib를 사용하면 spring app build, image build, image를 registry에 push하는 것을 정말 쉽게 할 수 있다. <code>build.gradle</code>에 다음의 내용을 추가하자.</p>
<pre><code class="language-groovy">plugins {
    id &#39;com.google.cloud.tools.jib&#39; version &#39;3.3.1&#39;
}

jib {
    to {
        image = &quot;localhost:49955/example&quot;
    }

    // local docker registry를 사용하기 때문에, http 허용
    allowInsecureRegistries true
}</code></pre>
<p>registry addon에서 제공한 포트번호를 사용한다는 점 잊지말자. 작성이 완료됐다면, 프로젝트 루트 경로에서 다음의 명령어를 입력한다.</p>
<pre><code>./gradlew jib</code></pre><p>위의 명령어를 실행이 완료됐다면, spring app image가 정상적으로 registry에 올라갔는지 확인하기 위해 이전에 사용했던 curl 명령어를 다시 사용하자.</p>
<pre><code>curl http://localhost:49955/v2/_catalog</code></pre><p>다음의 결과가 나와야 정상이다.</p>
<pre><code class="language-js">{&quot;repositories&quot;:[&quot;example&quot;]}</code></pre>
<p>이로써 spring app을 private registry에 올리는 것까지 완료했다. 이제 registry에 있는 spring app을 minikube에 deploy하자</p>
<h3 id="4-deploying-spring-app-to-minikube">4. Deploying spring app to minikube</h3>
<p>편의성을 위해 하나의 yaml파일에서 spring app에대한 deployment, service를 작성했다. 여기서 <code>image</code>에 <code>yourClusterIP</code>가 있는데, 이 부분을 지우고 본인의 registry cluster ip를 작성하면 된다. <code>/example</code>은 삭제하면 안된다. 참고로 이 <code>yml</code>파일은 프로젝트의 <code>deployment/example-app-deployment.yaml</code>에서 확인할 수 있다.
<br/></p>
<pre><code class="language-yml">apiVersion: apps/v1
kind: Deployment
metadata:
  name: myapp
spec:
  selector:
    matchLabels:
      app: myapp
  template:
    metadata:
      labels:
        app: myapp
    spec:
      containers:
        - name: myapp
          image: yourClusterIP/example
          imagePullPolicy: IfNotPresent
          resources:
            limits:
              memory: &quot;128Mi&quot;
              cpu: &quot;500m&quot;
          ports:
            - containerPort: 8080

---
apiVersion: v1
kind: Service
metadata:
  name: myapp-svc
spec:
  type: NodePort
  selector:
    app: myapp
  ports:
    - port: 80
      targetPort: 8080
      nodePort: 31212</code></pre>
<p>registry cluster ip를 확인하는 방법은 이전에 registry cluster가 존재한지 확인하기 위해 사용했던 명령어와 동일하다.</p>
<pre><code>kubectl get services --namespace kube-system</code></pre><p>작성자의 경우에는 <code>10.102.107.53</code>를 사용할 예정이다. 본인의 cluster ip에 맞게 설정했으면, kubectl명령어를 확인하여 deploy를 하자.</p>
<pre><code>kubectl apply -f example-app-deployment.yaml</code></pre><p>deploy가 정상적으로 작성됐는지 확인하기 위해 브라우저를 열고 url을 입력하자. 우리는 minikube에 있는 spring app에 대한 service를 통해 접근할 것이기 때문에, 아래의 명령어를 입력해야한다.</p>
<pre><code>minikube service myapp-svc</code></pre><p>그러면 2개의 URL이 출력된다는 것을 확인 할 수 있는데, 여기서 <code>127.0.0.1</code>(localhost)를 포함하는 URL를 복사하고 URL/ping를 브라우저에 입력한다.</p>
<pre><code>http://127.0.0.1:43987/ping</code></pre><p>그러면 화면에는 <code>pong</code>이라는 글자가 나오는 것을 확인할 수 있다. 이거와는 별개로 k9s를 이용하면 deployment와 service에 대한 자세한 내용을 쉽게 확인할 수 있다. 이 부분의 내용은 생략한다.</p>
<h2 id="4-pc-재부팅-후-registry-사용">4. PC 재부팅 후, registry 사용</h2>
<p>우리의 PC의 전원을 종료할 수 있다. 재부팅 이후의 minikube의 registry는 어떻게 사용할까??
방법은 간단한데 docker desktop을 실행하고, <code>minikube start</code>명령어를 입력하면 된다.</p>
<br/>

<p>사용된 코드는 <a href="https://github.com/Dev-Hi/minikube-docker-registry-test">https://github.com/Dev-Hi/minikube-docker-registry-test</a> 에서 확인할 수 있다.</p>
<h2 id="reference">Reference</h2>
<ul>
<li><a href="https://minikube.sigs.k8s.io/docs/handbook/registry/">https://minikube.sigs.k8s.io/docs/handbook/registry/</a></li>
</ul>
]]></description>
        </item>
    </channel>
</rss>