HKube Documentation

website·Indexed 31 days ago

https://hkube.org/

A cloud-native open source framework for running distributed pipelines of algorithms. HKube provides tools for managing Directed Acyclic Graph (DAG) pipelines, including a CLI (hkkubectl), a dashboard, and support for various integration methods via Docker, WebSockets, and a Code API for Java, Python, and JavaScript. It features KAI Scheduler for resource control, sidecar container support, and integrations with Tensorboard.

Tokens
14.8K
Snippets
77
Records
105
Agent score
54%

What's inside HKube

  1. Overview of KAI Scheduler integration

    The KAI Scheduler is a Kubernetes component that manages workload scheduling. It enables advanced resource control for algorithms, including GPU sharing (using fractions of a GPU) and queue prioritization.

    Prerequisites:

    Note: Resource limits defined here are not strictly enforced at runtime if an algorithm attempts to exceed its assigned resources.

  2. Overview of HKube distributed pipeline framework

    HKube is a cloud-native open source framework built on Kubernetes designed to run distributed pipelines of algorithms. It takes a Directed Acyclic Graph (DAG) as input and automatically parallelizes algorithms across a cluster. Key features include:

    • Language Agnostic: Supports any language via containerization.
    • Batch Algorithms: Ability to run multiple instances of the same algorithm to accelerate execution.
    • Hardware Optimization: Automatic container placement based on resource requirements and heuristics to maximize utilization.
    • Build API: Simplifies the process by handling container building and API integration.
  3. Overview of Hkube distributed algorithm framework

    Hkube is an open-source, container-based framework for running distributed pipelines of algorithms on Kubernetes. It is language-agnostic and optimizes hardware utilization by automatically placing containers based on resource requirements and AI-driven heuristics. It integrates with CNCF technologies like Prometheus and Jaeger for monitoring and exposes algorithm logs via stdout.
  4. Understand HKube Pipeline DAG concepts

    HKube pipelines are based on Directed Acyclic Graphs (DAG). In this structure, nodes are connected by directed edges (e.g., A -> B -> C). This architecture allows HKube to manage the ordering of node processing, handle data flow between nodes, and support parallel and batch processing.
  5. Trace algorithm execution with Jaeger

    Hkube uses OpenTracing to push traces to Jaeger by default. These traces are integrated into the Hkube dashboard for performance and execution analysis.
  6. Monitor HKube data using Dashboard Tables

    Use the 'Tables' panel in the HKube Dashboard to monitor HKube data, including viewing information about algorithm details and pipeline structures.
  7. Execute algorithms and pipelines using HKUBE Java Code API

    The HKUBE Java API allows for asynchronous execution of algorithms and pipelines. To obtain the result, you must wait for the APIExecutionFuture to complete using a polling mechanism or the .get() method.
    // Example of starting an algorithm, a stored pipeline, and a raw pipeline
    @Override
    public Object Start(Map args, IHKubeAPI hkubeAPI) throws Exception {
        Collection<Object> input = (Collection<Object>)args.get("input");
        Map action = (Map) input.iterator().next();
        String act = (String)action.get("action");
    
        if(act.equals("startAlg")) {
            List<String> list = new ArrayList<>();
            list.add("4");
            // Asynchronous call
            APIExecutionFuture futureResult = hkubeAPI.startAlgorithmAsynch("green-alg", list, true);
            return returnWhenExecDone(futureResult);
        }
    
        if(act.equals("startStored")) {
            APIExecutionFuture futureResult = hkubeAPI.startStoredPipeLineAsynch("simple", new HashMap());
            return returnWhenExecDone(futureResult);
        }
    
        if(act.equals("startRaw")) {
            // Define nodes for the raw pipeline
            INode jnkNode = createNode("one", "green-alg", "42");
            INode[] nodes = {jnkNode};
            APIExecutionFuture futureResult = hkubeAPI.startRawSubPipeLineAsynch("raw-pipe", nodes, new HashMap(), new HashMap(), new HashMap());
            return returnWhenExecDone(futureResult);
        }
        return 42;
    }
    
    // Helper to block until the asynchronous execution is complete
    private Map returnWhenExecDone(APIExecutionFuture future) {
        while (!future.isDone()) {
            try { Thread.sleep(100); } catch (InterruptedException e) { throw new RuntimeException(e); }
        }
        try {
            return future.get();
        } catch (InterruptedException | ExecutionException e) {
            throw new RuntimeException(e);
        }
    }
  8. Create and execute a pipeline of algorithms

    Pipelines are defined in a YAML file where nodes specify the sequence of algorithms. Each node requires a nodeName, the algorithmName to use, and input sources. Inputs can be external (e.g., flowInput.urls) or the output of a previous node (referenced by @nodeName).

    There are two ways to run a pipeline:

    1. Raw execution: Run a local YAML file immediately.
    2. Stored execution: Store the pipeline definition in Hkube first, then execute it by name.
    name: my-pipeline
    nodes:
    - nodeName: my-node-1
      algorithmName: my-alg
      input:
      - "flowInput.urls"
    - nodeName: my-node-2
      algorithmName: my-alg
      input:
      - "@my-node-1"
    - nodeName: my-node-3
      algorithmName: my-alg
      input:
      - "@my-node-2"

    Execute raw YAML

    hkubectl pipeline exec raw --f pipeline.yml

    Store and then execute by name

    hkubectl pipeline store -f pipeline.yml hkubectl pipeline exec stored my-pipeline

  9. Register an algorithm using hkubectl (No-Code Method)

    For a simple setup that avoids manual WebSocket and Docker configuration, use hkubectl to register an algorithm. This requires a configuration file (YAML or JSON) and the algorithm source code. The algorithm must implement a start method; initialize and stop methods are optional.
    name: my-alg
    env: python
    
    resources:
       cpu: 0.5
       gpu: 1
       mem: 512Mi
    
    code:
       path: /home/user/my-alg.tar.gz
       entryPoint: main.py

    Apply the configuration

    hkubectl algorithm apply --f algorithm.yml

  10. Define and apply algorithms using the HKube CLI

    To integrate an algorithm via the CLI, create a YAML or JSON descriptor file specifying the algorithm's name, environment, resource requirements (CPU, GPU, Memory), and the path to the code package with its entry point.
    # range.yml
    name: range
    env: python # options: python or javascript
    resources:
      cpu: 0.5
      gpu: 1 # optional
      mem: 512Mi
    
    code:
      path: /path-to-algorithm/range.tar.gz
      entryPoint: main.py

    Apply the algorithm using the CLI

    hkubectl algorithm apply --f range.yml

  11. Debug HKube algorithms using Python

    To debug a Python algorithm locally, install the hkube-python-wrapper package and use the Algorunner.Debug method, passing the debugging URL and the algorithm's start function.
    pip install hkube-python-wrapper
    from hkube_python_wrapper import Algorunner
    import algorithm.main as algorithm # the path of your "start" function
    
    def main():
            print("starting algorithm runner")
            # Replace <the debugging URL> with the actual URL obtained from HKube
            Algorunner.Debug("<the debugging URL>", algorithm.start)
    
    if __name__ == "__main__":
        main()
  12. Implement HKube algorithm communication via WebSocket

    HKube communicates with algorithms using WebSockets (native or socket.io). The algorithm must connect to ws://localhost:3000 and handle a JSON-based command protocol. The typical lifecycle involves receiving an initialize event, then a start event, and finally sending a done event with the results.
    // Connect to HKube
    this._socket = new WebSocket('ws://localhost:3000');
    
    // Handle incoming messages
    this._socket.on('message', (message) => {
        const payload = JSON.parse(message);
        switch (payload.command) {
          case 'initialize':
            this._initialize(payload);
            break;
          case 'start':
            this._start();
            break;
          case 'stop':
            this._stop();
            break;
        }
    });