1. 소개
이 사용방법(예제)에서는 공식 Java API를 사용하여 Kubernetes 리소스에 대한 CRUD 작업을 다룹니다.
기본 프로젝트 설정 및 실행 중인 클러스터에 대한 정보를 얻기 위해 이를 사용할 수 있는 다양한 방법 을 포함하여 이전 기사에서 이 API 사용의 기본 사항을 이미 다뤘습니다 .
일반적으로 Kubernetes 배포는 대부분 정적입니다. 만들고자 하는 것을 설명하는 일부 아티팩트(예: YAML 파일)를 만들고 DevOps 파이프라인에 제출합니다. 그런 다음 시스템의 일부는 새 구성 요소를 추가하거나 기존 구성 요소를 업그레이드할 때까지 동일하게 유지됩니다.
그러나 즉시 리소스를 추가해야 하는 경우가 있습니다. 일반적인 것은 사용자가 시작한 요청에 대한 응답으로 작업 을 실행하는 것입니다. 이에 대한 응답으로 애플리케이션은 백그라운드 작업을 시작하여 보고서를 처리하고 나중에 검색할 수 있도록 합니다.
여기서 중요한 점은 이러한 API를 사용하면 필요할 때만 리소스를 소비하고 나중에 해제할 수 있으므로 사용 가능한 인프라를 더 잘 활용할 수 있다는 것입니다.
2. 새 리소스 만들기
이 예에서는 Kubernetes 클러스터에 작업 리소스를 생성합니다. 작업은 다른 종류와 달리 완료될 때까지 실행되는 일종의 Kubernetes 워크로드입니다. 즉, 포드에서 실행 중인 프로그램이 종료되면 작업 자체가 종료됩니다. YAML 표현은 다른 리소스와 다르지 않습니다.
apiVersion: batch/v1
kind: Job
metadata:
namespace: jobs
name: report-job
labels:
app: reports
spec:
template:
metadata:
name: payroll-report
spec:
containers:
- name: main
image: report-runner
command:
- payroll
args:
- --date
- 2021-05-01
restartPolicy: Never
Kubernetes API는 동등한 Java 개체를 만드는 두 가지 방법을 제공합니다.
- 새로운 POJOS 생성 및 세터를 통해 필요한 모든 속성 채우기
- 유창한 API를 사용하여 Java 리소스 표현 구축
어떤 접근 방식을 사용할지는 대부분 개인 취향입니다. 여기에서는 빌드 프로세스가 YAML 대응 항목과 매우 유사하므로 유창한 접근 방식을 사용하여 V1Job 객체를 생성합니다.
ApiClient client = Config.defaultClient();
BatchV1Api api = new BatchV1Api(client);
V1Job body = new V1JobBuilder()
.withNewMetadata()
.withNamespace("report-jobs")
.withName("payroll-report-job")
.endMetadata()
.withNewSpec()
.withNewTemplate()
.withNewMetadata()
.addToLabels("name", "payroll-report")
.endMetadata()
.editOrNewSpec()
.addNewContainer()
.withName("main")
.withImage("report-runner")
.addNewCommand("payroll")
.addNewArg("--date")
.addNewArg("2021-05-01")
.endContainer()
.withRestartPolicy("Never")
.endSpec()
.endTemplate()
.endSpec()
.build();
V1Job createdJob = api.createNamespacedJob("report-jobs", body, null, null, null);
먼저 ApiClient 를 만든 다음 API 스텁 인스턴스를 만듭니다. 작업 리소스는 Batch API 의 일부이므로 클러스터의 API 서버를 호출하는 데 사용할 BatchV1Api 인스턴스 를 생성 합니다.
다음으로 모든 속성을 채우는 프로세스를 안내 하는 V1JobBuilder 인스턴스를 인스턴스화합니다. 중첩된 빌더의 사용에 주목하십시오. 중첩된 빌더를 "닫으려면" endXXX() 메서드를 호출해야 합니다. 그러면 부모 빌더로 돌아갑니다.
또는 중첩 객체를 직접 주입하기 위해 withXXX 메서드를 사용할 수도 있습니다. 이는 메타데이터, 레이블 및 어노테이션과 같은 공통 속성 집합을 재사용하려는 경우에 유용합니다.
마지막 단계는 API 스텁에 대한 호출입니다. 이렇게 하면 리소스 개체가 직렬화 되고 요청이 서버에 POST됩니다. 예상대로 API에는 동기(위에서 사용됨) 및 비동기 버전이 있습니다.
반환된 개체에는 생성된 작업과 관련된 메타데이터 및 상태 필드가 포함됩니다. Job 의 경우 status 필드를 사용하여 언제 완료되었는지 확인할 수 있습니다. 이 알림을 수신하기 위해 모니터링 리소스에 대한 기사에 제시된 기술 중 하나를 사용할 수도 있습니다.
3. 기존 리소스 업데이트
기존 리소스 업데이트는 수정하려는 필드가 포함된 PATCH 요청을 Kubernetes API 서버로 보내는 것으로 구성됩니다. Kubernetes 버전 1.16부터 해당 필드를 지정하는 네 가지 방법이 있습니다.
- JSON 패치(RFC 6092)
- JSON 병합 패치(RFC 7396)
- 전략적 병합 패치
- YAML 적용
그 중 마지막 것은 모든 병합 및 충돌 해결을 서버에 맡기므로 사용하기 가장 쉬운 것입니다. 우리가 해야 할 일은 수정하려는 필드가 있는 YAML 문서를 보내는 것입니다.
불행하게도 Java API는 이 부분적인 YAML 문서를 빌드하는 쉬운 방법을 제공하지 않습니다. 대신 PatchUtil 도우미 클래스에 의존하여 원시 YAML 또는 JSON 문자열을 보내야 합니다. 그러나 ApiClient 개체를 통해 사용할 수 있는 내장 JSON 직렬 변환기를 사용 하여 가져올 수 있습니다.
V1Job patchedJob = new V1JobBuilder(createdJob)
.withNewMetadata()
.withName(createdJob.getMetadata().getName())
.withNamespace(createdJob.getMetadata().getNamespace())
.endMetadata()
.editSpec()
.withParallelism(2)
.endSpec()
.build();
String patchedJobJSON = client.getJSON().serialize(patchedJob);
PatchUtils.patch(
V1Job.class,
() -> api.patchNamespacedJobCall(
createdJob.getMetadata().getName(),
createdJob.getMetadata().getNamespace(),
new V1Patch(patchedJobJSON),
null,
null,
"baeldung",
true,
null),
V1Patch.PATCH_FORMAT_APPLY_YAML,
api.getApiClient());
여기에서는 createNamespacedJob() 에서 반환된 개체 를 템플릿으로 사용하여 패치 버전을 구성합니다. 이 경우 병렬 처리 값을 1에서 2로 늘리고 다른 모든 필드는 변경하지 않습니다. 여기서 중요한 점은 수정된 리소스를 빌드할 때 withNewMetadata() 를 사용해야 한다는 것 입니다. 이렇게 하면 리소스를 만든 후 반환된 개체에 있는 관리 필드를 포함하는 개체를 빌드하지 않습니다. 관리 필드에 대한 전체 설명과 Kubernetes에서 사용되는 방법은 설명서 를 참조하십시오 .
수정된 필드를 사용하여 개체를 만든 후에는 serialize 메서드 를 사용하여 JSON 표현으로 변환합니다 . 그런 다음 이 직렬화된 버전을 사용하여 PATCH 호출의 페이로드로 사용되는 V1Patch 개체를 구성합니다. patch 메서드는 또한 요청에 있는 데이터의 종류를 알려주는 추가 인수를 사용합니다. 우리의 경우 이것은 라이브러리가 HTTP 요청에 포함된 Content-Type 헤더 로 사용하는 PATCH_FORMAT_APPLY_YAML 입니다.
fieldManager 매개 변수 에 전달 된 "baeldung" 값 은 리소스의 필드를 조작하는 행위자 이름을 정의합니다. Kubernetes는 둘 이상의 클라이언트가 동일한 리소스를 수정하려고 할 때 내부적으로 이 값을 사용하여 최종 충돌을 해결합니다. 또한 force 매개 변수에 true 를 전달 합니다. 즉, 수정된 모든 필드의 소유권을 갖습니다.
4. 리소스 삭제
이전 작업과 비교할 때 리소스 삭제는 매우 간단합니다.
V1Status response = api.deleteNamespacedJob(
createdJob.getMetadata().getName(),
createdJob.getMetadata().getNamespace(),
null,
null,
null,
null,
null,
null ) ;
여기서는 deleteNamespacedJob 메서드를 사용하여 이 특정 종류의 리소스에 대한 기본 옵션을 사용하여 작업을 제거합니다. 필요한 경우 마지막 매개 변수를 사용하여 삭제 프로세스의 세부 정보를 제어할 수 있습니다. 이것은 V1DeleteOptions 개체의 형식을 취하며, 종속 리소스에 대한 유예 기간 및 계단식 동작을 지정하는 데 사용할 수 있습니다.
5. 결론
이 기사에서는 Java Kubernetes API 라이브러리를 사용하여 Kubernetes 리소스를 조작하는 방법을 다루었습니다. 늘 그렇듯이 예제의 전체 소스 코드는 GitHub 에서 찾을 수 있습니다 .