Skip to main content

KRules Command Line

Project description

KRules CLI

Krules CLI is a tool allow you to quickly create a project based on KRules <https://github.com/airspot-dev/krules-core>_ and organize your microservices in a hierarchical structure.

Initial steps

Init project tree


To initialize a new **Project** run:

.. code:: bash

    krules-py project init your/project/path

| In case one or more directory of path does not exist, the script will create them for you.
| Moreover a *default* `profile <#managing-profiles>`__ will be generated.

To generate *default* profile some params must be prompted, but sometimes you need to avoid user interaction, maybe because you want integrate a CI/CD solution. This could be achieved using this optional params:

-  *--name [default current folder name]*: set project name;
-  -n --namespace [default default] : set in which namespace will be deployed your components;
-  -d --docker-registry. : set docker registry with which to push and deploy your image;
-  -i --image-base  : override ruleset image base.

Example

.. code:: bash

    krules-py project init . --name my-project

The output will be:

::

    . my-project
    │
    ├── base
    │   │
    │   ├── Dockerfile
    │   ├── ipython_config.py
    │   ├── Makefile
    │   ├── VERSION
    │   ├── app
    │   │   │
    │   │   ├── env.py
    │   │   └── app_functions
    │   │       │
    │   │       └── __init__.py
    │   └── k8s
    │       │
    │       ├── brokers.yaml
    │       ├── config-krules.yaml
    │       ├── config-krules-subjects-mongodb.yaml
    │       ├── config-krules-subjects-mongodb-auth.yaml
    │       ├── config-krules-subjects-redis.yaml
    │       ├── config-krules-subjects-redis-auth.yaml
    │       ├── event-display.yaml
    │       ├── kustomization.yaml
    │       └── triggers.yaml
    └── rulesets
        │
        └── patches.yaml


Config subject storage support

The next step is to choose the subject storage support.

The default storage class can be used just for local testing so you have to use another one in production environment, at now you can choose between redis and mongodb

Go to base/app/env.py to enable your preferred storage support.

First of all remove the default implementation:

.. code:: python

from krules_core.tests.subject.sqlite_storage import SQLLiteSubjectStorage
subject_storage_factory.override(
   providers.Factory(lambda x: SQLLiteSubjectStorage(x, ":memory:"))
)

If, for example, you want to use redis support uncomment this code part:

.. code:: python

# Redis subjects storage support
subjects_redis_storage_settings = settings_factory() \
    .get("subjects-backends") \
    .get("redis")
from redis_subjects_storage import storage_impl as redis_storage_impl

subject_storage_factory.override(
    providers.Factory(
        lambda x: redis_storage_impl.SubjectsRedisStorage(x, subjects_redis_storage_settings.get("url"))
    )
)

Then in base/k8s update ConfigMap and authorization data related to the storage support you choose. Continuing with redis example.

config-krules-subject-redis-auth.yaml

.. code:: yaml

apiVersion: v1
data:
password: cGFzc3dvcmQ= # replace with your redis password in base64 format
kind: Secret
metadata:
  name: config-krules-subjects-redis-auth
type: Opaque

config-krules-subject-redis.yaml

.. code:: yaml

apiVersion: v1 kind: ConfigMap metadata: name: config-krules-subjects-redis data: config_subjects_redis.yaml: | url: redis://:${KRULES_SUBJECTS_REDIS_PASSWORD}@redis.address/0 # replace with your redis address

Remember to include them in the kustomization.yaml.

The last step is to make those configurations known to your rulesets.

In rulesets/patches.yaml uncomment the patch <#how-to-use>__ related to your chosen storage support.

.. code:: yaml

## Redis subjects backend
kinds:
  - serving.knative.dev/v1beta1:Service
  - apps/v1:Deployment
labelsMatch:
  - airspot.krules.dev/type: ^ruleset$
patch:
  spec:
    template:
      spec:
        containers:
          - patch__0:
            env:
              - name: KRULES_SUBJECTS_REDIS_PASSWORD
                valueFrom:
                  secretKeyRef:
                    name: config-krules-subjects-redis-auth
                    key: password
            volumeMounts:
              - name: config-krules-subjects-redis-volume
                mountPath: /krules/config/subjects-backends/redis

      volumes:
        - name: config-krules-subjects-redis-volume
          configMap:
            name: config-krules-subjects-redis

Build and push base image


Go to **base** folder and run *make*.

**make** command will take care of each needed operation to build and push your base image correctly. You can also run each step individually:

- **VERSION**: Detect changes checking your Dockerfile and each your .py file in the **base/app** folder and possibly build a new base image version;
- **push**: If there is a new image build in your local registry push it to your Docker repository;
- .lastResources: Apply all yaml in **k8s** folder to your namespace.
- clean: Clean all files generated by **make** command, useful to relaunch it without make any changes to your files.

Working with Rulesets
----------------------

Init Ruleset tree
~~~~~~~~~~~~~~~~~~

To create a new **Ruleset** go to **rulesets** folder and run:

.. code:: bash

    krules-py ruleset create my-ruleset

The output will be:

::

    . my-ruleset
    │
    ├── Dockerfile.origin
    ├── Makefile
    ├── VERSION
    ├── app
    │   │
    │   └── rules.py
    └── k8s
        │
        ├── kustomization.yaml
        └── service.yaml

Deploy your Ruleset
~~~~~~~~~~~~~~~~~~~

To deploy your code on Kubernetes got to your ruleset folder and run
*make*. *make* command will take care of each needed operation to deploy your ruleset correctly detecting files changes.

You can also run each step individually:

- **Dockerfile**: Detect changes in your Dockerfile.origin and generate a new Dockerfile if needed.
So, if you want to change the Dockerfile don't modify directly it but edit the *Dockerfile.origin*;
- **VERSION**: Detect changes checking your Dockerfile and each your .py file in the rulesset **app** folder and possibly build a new rulesset image version;
- **push**: If there is a new image build in your local registry push it to your Docker repository;
- .lastResources: Apply all yaml in **k8s** folder to your namespace.
- clean: Clean all files generated by **make** command, useful to relaunch it without make any changes to your files.

Each ruleset inherit your project image base, so if you change it you have to redeploy your ruleset using:

.. code:: bash

    make clean && make

Generate your Ruleset manifest (using kustomize)

The KRules CLI integrate kubectl kustomize <https://github.com/kubernetes-sigs/kustomize>_. command. In added to the kustomize standard functions, it provide to the user another patches logic.

Usage:

.. code:: bash

krules-py ruleset patch

patch command apply each patches.yaml file from the project root to the ruleset folder, so it is possible to define some patches shared by all rulesets or by group of ruleset.

Example:

::

. rulesets
│
├── patches.yaml
├── my-group
│   │
│   ├── my-ruleset-2/
│   ├── my-ruleset-3/
│   ├── my-ruleset-4/
│   └── patches.yaml
└── my-ruleset-1
    │
    ...
    ├── kustomization.yaml
    └── service.yaml

rulesets/patches.yaml will be applied to all rulesets, while rulesets/my-group/patches.yaml will modified just the rulesets inside my-group folder

Custom path


*patch* command search for kustomization file in the current folder or
in k8s one. If you put your file in another path you can use the
**path** parameter

Usage:

.. code:: bash

    krules-py ruleset patch -p [--path] custom/path

Warning
-------

*path* param refer to folder containing the kustomization file not to
the file itself.

How to use
~~~~~~~~~~

*Basic Usage*

Supposing you define this 3 files:

**service.yaml**

.. code:: yaml

    apiVersion: v1
    kind: Service
    metadata:
      name: my-service
    spec:
      template:
        spec:
          contatiners:
          - name: my-container
    ---

**triggers/my-trigger.yaml**

.. code:: yaml

    apiVersion: eventing.knative.dev/v1alpha1
    kind: Trigger
    metadata:
      name: my-trigger

**kustomization.yaml**

.. code:: yaml

    commonLabels:
      airspot.krules.dev/ruleset: my-ruleset
    resources:
    - service.yaml
    - triggers/my-trigger.yaml

You can override the previous components creating a file named
*patches.yaml* in some of parent folders

.. code:: yaml

    kinds:
      - v1:Service
      - serving.knative.dev/v1alpha1:Service
    patch:
      metadata:
        labels:
          app: my-app
    ---
    kinds:
      - serving.knative.dev/v1alpha1:Trigger
    patch:
      spec:
        broker: my-broker

**kinds** : list of kinds of components will be affected from the patch.
Format: : **patch** : list of field will be modify with this patch
**labelsMatch**: list of regex to filter components by metadata labels.

The output will be:

.. code:: yaml

    apiVersion: v1
    kind: Service
    metadata:
      name: my-service
      labels:
        airspot.krules.dev/ruleset: my-ruleset
        app: my-app
    spec:
      template:
        spec:
          contatiners:
          - name: my-container

    ---
    apiVersion: eventing.knative.dev/v1alpha1
    kind: Trigger
    metadata:
      name: my-trigger
      labels:
        airspot.krules.dev/ruleset: my-ruleset
    spec:
      broker: my-broker
    ---

*Adding a second container*

To add element to a list just define the new elements in the patch
inside the list key.

**service.yaml**

.. code:: yaml

    apiVersion: v1
    kind: Service
    metadata:
      name: my-service
    spec:
      template:
        spec:
          contatiners:
          - name: my-first-container
    ---

**patches.yaml**

.. code:: yaml

    kinds:
      - v1:Service
      - serving.knative.dev/v1alpha1:Service
    patch:
      spec:
        template:
          spec:
            containers:
              - name: my-second-container

Output:

.. code:: yaml

    apiVersion: v1
    kind: Service
    metadata:
      name: my-service
    spec:
      template:
        spec:
          contatiners:
          - name: my-first-container
          - name: my-second-container
    ---

*Adding volumeMount just to a specific container*

To override a single list element use **patch\__<index>** keyword, where
*index* indicates the index of the element of the list to be
modified.

**service.yaml**

.. code:: yaml

    apiVersion: v1
    kind: Service
    metadata:
      name: my-service
    spec:
      template:
        spec:
          contatiners:
          - name: my-first-container
          - name: my-second-container
          - name: my-third-container
    ---

**patches.yaml**

.. code:: yaml

    kinds:
      - v1:Service
      - serving.knative.dev/v1alpha1:Service
    labelsMatch:
      - app: my-app
    patch:
      spec:
        template:
          spec:
            containers:
              - patch__1:
                  volumeMounts:
                    - name: my-volume
                      mountPath: /configs/

            volumes:
              - name: my-volume
                configMap:
                  name: my-config

Output:

.. code:: yaml

    apiVersion: v1
    kind: Service
    metadata:
      name: my-service
    spec:
      template:
        spec:
          contatiners:
            - name: my-first-container
            - name: my-second-container
              volumeMounts:
                    - name: my-volume
                      mountPath: /configs/
            - name: my-third-container
          volumes:
            - name: my-volume
              configMap:
                name: my-config
    ---

*Update a specific container image*

**service.yaml**

.. code:: yaml

    apiVersion: v1
    kind: Service
    metadata:
      name: my-service
    spec:
      template:
        spec:
          containers:
          - name: my-container
          - name: my-other-container
    ---

.. code:: bash

    krules-py ruleset patch set-image my-container=my-docker-registry/my-image:latest

Output:

**service.yaml**

.. code:: yaml

    apiVersion: v1
    kind: Service
    metadata:
      name: my-service
    spec:
      template:
        spec:
          containers:
          - name: my-container
            image: my-docker-registry/my-image:latest
          - name: my-other-container
    ---

Custom ruleset template

It is possible that default ruleset template does not completely satisfy your requirements. You can override it using:

.. code:: bash

krules-py gen-rs-template your_template_dir [--set-default]

The selected template directory must be contained in your project. ** --set-default ** flag set your directory as the default one for each ruleset. The output will be:

::

. your_template_dir
│
├── Dockerfile.origin
├── Makefile
├── VERSION
├── app
│    │
│    └── rules.py
└── k8s
     │
     ├── kustomization.yaml
     ├── service.yaml
     └── triggers.yaml

To reset default rulesets template folder use:

.. code:: bash

krules-py gen-rs-template --unset-default

Managing Version

Both base and rulesets folders contains a file VERSION. This file contains your current local image version. When you run make in a ruleset folder your local image will be deployed only if its version is greater than the cluster one.

Managing profiles



The KRules CLI provides also a profiles handler. A profile contains all
useful defaults value as docker registry and kubernetes namespace.

Add new profile
---------------

.. code:: bash

    krules-py profile add myProfile

**Optional arguments**

-  --set-default: set the new profile as the default one;
-  -ns --namespace: set profile namespace;
-  -d --docker-registry: set profile Docker registry.

Set/Get default profile
-----------------------

.. code:: bash

    $ krules-py profile set myProfile
    $
    $ krules-py profile get
    $ myProfile

To list all available profiles run

.. code:: bash

    krule-py profile list

Set/Get profile value
---------------------

.. code:: bash

    $ krule-py profile set-value namespace myNamespace
    $
    $ krule-py profile get-value namespace
    $ myNamespace

To print all profile values run

.. code:: bash

    krule-py profile values

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Files for krules-py-cli, version 0.4.0
Filename, size File type Python version Upload date Hashes
Filename, size krules-py-cli-0.4.0.tar.gz (24.7 kB) File type Source Python version None Upload date Hashes View

Supported by

Pingdom Pingdom Monitoring Google Google Object Storage and Download Analytics Sentry Sentry Error logging AWS AWS Cloud computing DataDog DataDog Monitoring Fastly Fastly CDN DigiCert DigiCert EV certificate StatusPage StatusPage Status page