Get Started

This tutorial is for those who have already completed Get Started. Please refer to Prepare the Kubernetes Cluster and others there.

Deploy Vald on Kubernetes Cluster

This chapter shows how to deploy Vald using Helm and run it on your Kubernetes cluster.
In this tutorial, you will deploy the basic configuration of Vald that is consisted of vald-agent-faiss, vald-lb-gateway, vald-discoverer, and vald-manager-index.

  1. Clone the repository

    git clone https://github.com/vdaas/vald.git && \
    cd vald
    
  2. Confirm which cluster to deploy

    kubectl cluster-info
    
  3. Edit Configurations

    Set the parameters for connecting to the vald-lb-gateway through Kubernetes ingress from the external network. Please set these parameters.

    vim example/helm/values.yaml
    ===
    ## vald-lb-gateway settings
    gateway:
      lb:
        ...
        ingress:
          enabled: true
          # TODO: Set your ingress host.
          host: localhost
          # TODO: Set annotations which you have to set for your k8s cluster.
          annotations:
            ...
    ## vald-agent-faiss settings
    agent:
      algorithm: faiss
      image:
        repository: vdaas/vald-agent-faiss
        tag: latest
      faiss:
        auto_index_check_duration: 1m
        auto_index_duration_limit: 24h
        auto_index_length: 10
        auto_save_index_duration: 35m
        dimension: 784
        enable_copy_on_write: false
        enable_in_memory_mode: true
        enable_proactive_gc: true
        index_path: ""
        initial_delay_max_duration: 3m
        load_index_timeout_factor: 1ms
        m: 8  # dimension % m == 0, train size >= 2^m(or nlist) * minPointsPerCentroid
        max_load_index_timeout: 10m
        method_type: "ivfpq"
        metric_type: "innerproduct"
        min_load_index_timeout: 3m
        nbits_per_idx: 8
        nlist: 100
          ...
    

    Note:
    If you decided to use port-forward instead of ingress, please set gateway.lb.ingress.enabled to false.

  4. Deploy Vald using Helm

    Add vald repo into the helm repo.

    helm repo add vald https://vald.vdaas.org/charts
    

    Deploy vald on your Kubernetes cluster.

    helm install vald vald/vald --values example/helm/values.yaml
    
  5. Verify

    When finish deploying Vald, you can check the Vald’s pods status following command.

    kubectl get pods
    
    Example output
    If the deployment is successful, all Vald components should be running.
    NAME                                         READY   STATUS      RESTARTS   AGE
    vald-agent-faiss-0                           1/1     Running     0          7m12s
    vald-agent-faiss-1                           1/1     Running     0          7m12s
    vald-agent-faiss-2                           1/1     Running     0          7m12s
    vald-agent-faiss-3                           1/1     Running     0          7m12s
    vald-agent-faiss-4                           1/1     Running     0          7m12s
    vald-discoverer-7f9f697dbb-q44qh             1/1     Running     0          7m11s
    vald-lb-gateway-6b7b9f6948-4z5md             1/1     Running     0          7m12s
    vald-lb-gateway-6b7b9f6948-68g94             1/1     Running     0          6m56s
    vald-lb-gateway-6b7b9f6948-cvspq             1/1     Running     0          6m56s
    vald-manager-index-74c7b5ddd6-jrnlw          1/1     Running     0          7m12s
    
    kubectl get ingress
    
    Example output
    NAME                      CLASS    HOSTS       ADDRESS        PORTS   AGE
    vald-lb-gateway-ingress   <none>   localhost   192.168.16.2   80      7m43s
    
    kubectl get svc
    
    Example output
    NAME                   TYPE        CLUSTER-IP   EXTERNAL-IP   PORT(S)             AGE
    kubernetes             ClusterIP   10.43.0.1    <none>        443/TCP             9m29s
    vald-agent-faiss       ClusterIP   None         <none>        8081/TCP,3001/TCP   8m48s
    vald-discoverer        ClusterIP   None         <none>        8081/TCP,3001/TCP   8m48s
    vald-manager-index     ClusterIP   None         <none>        8081/TCP,3001/TCP   8m48s
    vald-lb-gateway        ClusterIP   None         <none>        8081/TCP,3001/TCP   8m48s
    

Run Example Code

In this chapter, you will execute insert, search, and delete vectors to your Vald cluster using the example code.
The Fashion-MNIST is used as a dataset for indexing and search query.

The example code is implemented in Go and using vald-client-go, one of the official Vald client libraries, for requesting to Vald cluster. Vald provides multiple language client libraries such as Go, Java, Node.js, Python, etc. If you are interested, please refer to SDKs.

  1. Port Forward(option)

    If you do not use Kubernetes Ingress, port-forward is required to make requests from your local environment.

    kubectl port-forward deployment/vald-lb-gateway 8081:8081
    
  2. Download dataset

    Download Fashion-MNIST that is used as a dataset for indexing and search query.

    Move to the working directory

    cd example/client
    

    Download Fashion-MNIST testing dataset

    wget http://ann-benchmarks.com/fashion-mnist-784-euclidean.hdf5
    
  3. Run Example

    We use example/client/main.go to run the example.
    This example will insert and index 400 vectors into the Vald from the Fashion-MNIST dataset via gRPC. And then after waiting for indexing, it will request for searching the nearest vector 10 times. You will get the 10 nearest neighbor vectors for each search query.
    Run example codes by executing the below command.

    go run main.go
    
    The detailed explanation of example code is here
    This will execute 6 steps.
    1. init

      • Import packages

        example code
        package main
        
        import (
            "context"
            "encoding/json"
            "flag"
            "time"
        
            "github.com/kpango/fuid"
            "github.com/kpango/glg"
            "github.com/vdaas/vald-client-go/v1/payload"
            "github.com/vdaas/vald-client-go/v1/vald"
        
            "gonum.org/v1/hdf5"
            "google.golang.org/grpc"
        )
        
      • Set variables

        • The constant number of training datasets and test datasets.

          example code
          const (
              insertCount = 400
              testCount = 20
          )
          
        • The variables for configuration.

          example code
          const (
              datasetPath         string
              grpcServerAddr      string
              indexingWaitSeconds uint
          )
          
      • Recognition parameters.

        example code
        func init() {
            flag.StringVar(&datasetPath, "path", "fashion-mnist-784-euclidean.hdf5", "set dataset path")
            flag.StringVar(&grpcServerAddr, "addr", "127.0.0.1:8081", "set gRPC server address")
            flag.UintVar(&indexingWaitSeconds, "wait", 60, "set indexing wait seconds")
            flag.Parse()
        }
        
    2. load

      • Loading from Fashion-MNIST dataset and set id for each vector that is loaded. This step will return the training dataset, test dataset, and ids list of ids when loading is completed with success.

        example code
        ids, train, test, err := load(datasetPath)
        if err != nil {
            glg.Fatal(err)
        }
        
    3. Create the gRPC connection and Vald client with gRPC connection.

      example code
      ctx := context.Background()
      
      conn, err := grpc.NewClient(grpcServerAddr, grpc.WithInsecure())
      if err != nil {
          glg.Fatal(err)
      }
      
      client := vald.NewValdClient(conn)
      
    4. Insert and Index

      • Insert and Indexing 400 training datasets to the Vald agent.

        example code
        for i := range ids [:insertCount] {
            _, err := client.Insert(ctx, &payload.Insert_Request{
                Vector: &payload.Object_Vector{
                    Id:     ids[i],
                    Vector: train[i],
                },
                Config: &payload.Insert_Config{
                    SkipStrictExistCheck: true,
                },
            })
            if err != nil {
                glg.Fatal(err)
            }
            if i%10 == 0 {
                glg.Infof("Inserted %d", i)
            }
        }
        
      • Wait until indexing finish.

        example code
        wt := time.Duration(indexingWaitSeconds) * time.Second
        glg.Infof("Wait %s for indexing to finish", wt)
        time.Sleep(wt)
        
    5. Search

      • Search 10 neighbor vectors for each 20 test datasets and return a list of the neighbor vectors.

      • When getting approximate vectors, the Vald client sends search config and vector to the server via gRPC.

        example code
        glg.Infof("Start search %d times", testCount)
        for i, vec := range test[:testCount] {
            res, err := client.Search(ctx, &payload.Search_Request){
                Vector: vec,
                Config: &payload.Search_Config{
                    Num: 10,
                    Radius: -1,
                    Epsilon: 0.1,
                    Timeout: 100000000,
                }
            }
            if err != nil {
                glg.Fatal(err)
            }
        
            b, _ := json.MarshalIndent(res.GetResults(), "", " ")
            glg.Infof("%d - Results : %s\n\n", i+1, string(b))
            time.Sleep(1 * time.Second)
        }
        
    6. Remove

      • Remove 400 indexed training datasets from the Vald agent.

        example code
        for i := range ids [:insertCount] {
            _, err := client.Remove(ctx, &payload.Remove_Request{
                Id: &payload.Object_ID{
                    Id: ids[i],
                },
            })
            if err != nil {
                glg.Fatal(err)
            }
            if i%10 == 0 {
                glg.Infof("Removed %d", i)
            }
        }
        

Cleanup

In the last, you can remove the deployed Vald Cluster by executing the below command.

helm uninstall vald

References

See also