Рубрики
Без рубрики

Напишите плагин kubectl на Java с помощью jbing и fabric 8

Если вы часто используете kubectl, вы можете обнаружить, что выполняете одну и ту же последовательность команд… С тегом kubernetes, java.

Если вы часто используете kubectl , вы можете обнаружить, что снова и снова выполняете одну и ту же последовательность команд.

Частым случаем использования, дающим такие последовательности, является просмотр секрета , для которого требуется найти секрет и расшифровать его форму base64.

В этом уроке я расскажу, как создать плагин kubectl на Java. Плагин сделает следующее после того, как мы выполним команду kubectl lp :

  • Перечислите модули с их именем, статусом и значением по умолчанию пустое сообщение
  • Если модуль не находится в запущенном состоянии, отобразите значок 🔥 перед его строкой, в противном случае отобразите значок ✅
  • Отобразите сообщение о том, почему модуль не запущен

Jбанг

Чтобы написать плагин на Java, я буду использовать jbang . Bang – это фреймворк, который переносит сценарии в область Java.

Если у вас еще не установлен Jbang, просто выполните следующее:

brew install jbangdev/tap/jbang

Или проверьте документацию , чтобы найти инструкции для вашей операционной системы.

Следующий шаг – создать шаблон с инициализатором, я вызову скрипт lp для список модулей :

jbang init --template=cli lp.java

Это создаст полностью функциональный скрипт lp.java со следующим содержанием:

///usr/bin/env jbang "$0" "$@" ; exit $?
//DEPS info.picocli:picocli:4.5.0

import picocli.CommandLine;
import picocli.CommandLine.Command;
import picocli.CommandLine.Parameters;

import java.util.concurrent.Callable;

@Command(name = "lp", mixinStandardHelpOptions = true, version = "lp 0.1",
        description = "lp made with jbang")
class lp implements Callable {

    @Parameters(index = "0", description = "The greeting to print", defaultValue = "World!")
    private String greeting;

    public static void main(String... args) {
        int exitCode = new CommandLine(new lp()).execute(args);
        System.exit(exitCode);
    }

    @Override
    public Integer call() throws Exception { // your business logic goes here...
        System.out.println("Hello " + greeting);
        return 0;
    }
}

Это простой шаблон, который приветствует вас, попробуйте выполнить его с помощью следующей команды:

$ jbang lp.java Chris
Hello Chris
$

Добавление зависимостей в ваши сценарии так же просто, как добавление комментария в начале файла с артефактом зависимостей:

//DEPS io.fabric8:kubernetes-client:4.13.0

Здесь мы добавили клиентскую библиотеку fabric8 kubernetes. Пока мы этим занимаемся, давайте посмотрим, как работает этот клиент.

Ткань 8

Клиент fabric8 kubernetes – это библиотека, которая предоставляет доступ к API Rest Kubernetes через простой и удобный для пользователя DSL.

Например, вот как вы находите только те модули, которые не находятся в состоянии РАБОТАЕТ :

kc.pods().list().getItems()
                .stream()
                .filter(pod -> !PodStatusUtil.isRunning(pod))
                .collect(Collectors.toList());

В нашем сценарии мы будем использовать клиент для извлечения всех модулей и создания новой модели домена Информация о модуле с именем, состоянием и дополнительным сообщением:

private static List getPods() {
        KubernetesClient kc;
        try {
            kc = new DefaultKubernetesClient();
        } catch (Exception e) {
            throw new RuntimeException("Unable to create default Kubernetes client", e);
        }

        return kc.pods().list().getItems().stream().map(pod -> {
            PodInfoState state = PodStatusUtil.isRunning(pod) ? PodInfoState.RUNNING : PodInfoState.FAILING;
            String message = null;
            if (!state.equals(PodInfoState.RUNNING)) {
                message = PodStatusUtil.getContainerStatus(pod).get(0).getState().getWaiting().getMessage();
            }

            return new PodInfo(pod.getMetadata().getName(), state, message);
        }).collect(Collectors.toList());
    }

    static class PodInfo {

        private final String name;
        private final PodInfoState state;
        private final String message;

        public PodInfo(String name, PodInfoState state, String message) {
            this.name = name;
            this.state = state;
            this.message = message;
        }

        public String getName() {
            return name;
        }

        public PodInfoState getState() {
            return state;
        }

        public String getMessage() {
            return message;
        }
    }

    enum PodInfoState {
        RUNNING,
        FAILING
    }

Мы также добавим библиотеку j-textutils java, чтобы мы могли отображать все в таблице

//DEPS com.massisframework:j-text-utils:0.3.4
private static void printTable(List list) {
        final Object[][] tableData = list.stream()
                .map(podInfo -> new Object[]{
                        podInfo.getState().equals(PodInfoState.RUNNING) ? CHECK_MARK : FIRE,
                        podInfo.getName(),
                        podInfo.getState(),
                        podInfo.getMessage()
                })
                .toArray(Object[][]::new);
        String[] columnNames = {"", "name", "state", "message"};
        new TextTable(columnNames, tableData).printTable();
    }

Полный код можно найти здесь: https://github.com/ikwattro/kubectl-plugin-java-jbang

Если мы запустим наш сценарий, мы сможем увидеть его в действии:

$ jbang lp.java
[jbang] Building jar...
SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
SLF4J: Defaulting to no-operation (NOP) logger implementation
SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.
________________________________________________________________________________________
|   | name                             | state  | message                               |
|=======================================================================================|
| ✅ | neo4j-neo4j-core-0               | RUNNING|                                       |
| ✅ | nginx-app                        | RUNNING|                                       |
| 🔥| nginx-deployment-77fbdb7874-8gkcr| FAILING| Back-off pulling image "nginx2:1.16.1"|
| 🔥| nginx-deployment-77fbdb7874-8jps7| FAILING| Back-off pulling image "nginx2:1.16.1"|
| 🔥| nginx-deployment-77fbdb7874-vx27r| FAILING| Back-off pulling image "nginx2:1.16.1"|
| ✅ | postgres                         | RUNNING|                                       |
| ✅ | coredns-f9fd979d6-qwgfm          | RUNNING|                                       |
| ✅ | etcd-minikube                    | RUNNING|                                       |
| ✅ | kube-apiserver-minikube          | RUNNING|                                       |
| ✅ | kube-controller-manager-minikube | RUNNING|                                       |
| ✅ | kube-proxy-s5bcc                 | RUNNING|                                       |
| ✅ | kube-scheduler-minikube          | RUNNING|                                       |
| ✅ | storage-provisioner              | RUNNING|                                       |
$

Расширение kubectl

Расширение kubectl очень просто, так как в нем в основном 3 соглашения:

  • Вам нужно разместить свой скрипт на своем пути
  • Имя скрипта должно начинаться с кубектл- и не иметь расширения
  • Сценарий должен быть исполняемым

Нам нужно будет обратить внимание, потому что при создании шаблона blank самая первая строка была прокомментирована для хорошей игры с IDE при редактировании скрипта.

Просто раскомментируйте строку:

#!/usr/bin/env jbang

Во-вторых, мы скопируем скрипт на наш путь:

cp lp.java /usr/local/bin/kubectl-lp

И сделайте его исполняемым:

chmod +x /usr/local/bin/kubectl-lp

Теперь вы можете запустить kubectl lp для перечисления ваших модулей:

$ kubectl lp
SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
SLF4J: Defaulting to no-operation (NOP) logger implementation
SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.
________________________________________________________________________________________
|   | name                             | state  | message                               |
|=======================================================================================|
| ✅ | neo4j-neo4j-core-0               | RUNNING|                                       |
| ✅ | nginx-app                        | RUNNING|                                       |
| 🔥| nginx-deployment-77fbdb7874-8gkcr| FAILING| Back-off pulling image "nginx2:1.16.1"|
| 🔥| nginx-deployment-77fbdb7874-8jps7| FAILING| Back-off pulling image "nginx2:1.16.1"|
| 🔥| nginx-deployment-77fbdb7874-vx27r| FAILING| Back-off pulling image "nginx2:1.16.1"|
| ✅ | postgres                         | RUNNING|                                       |
| ✅ | coredns-f9fd979d6-qwgfm          | RUNNING|                                       |
| ✅ | etcd-minikube                    | RUNNING|                                       |
| ✅ | kube-apiserver-minikube          | RUNNING|                                       |
| ✅ | kube-controller-manager-minikube | RUNNING|                                       |
| ✅ | kube-proxy-s5bcc                 | RUNNING|                                       |
| ✅ | kube-scheduler-minikube          | RUNNING|                                       |
| ✅ | storage-provisioner              | RUNNING|                                       |
$

Вывод

Инструмент Kubectl легко расширяется, и Jibing позволяет быстро писать сценарии на Java, где мы, вероятно, обратились бы к Python до того, как этот инструмент появился.

Рекомендации:

Оригинал: “https://dev.to/ikwattro/write-a-kubectl-plugin-in-java-with-jbang-and-fabric8-566”