first commit

This commit is contained in:
Beyhan Oğur
2026-04-26 21:52:23 +03:00
commit 880f412e2c
2662 changed files with 866266 additions and 0 deletions

View File

@@ -0,0 +1,45 @@
# Bifrost on Kubernetes
Deploys Bifrost on any existing Kubernetes cluster using a Deployment, PVC, and optional Ingress + HPA.
## Prerequisites
- A running Kubernetes cluster with `kubectl` access
- A kubeconfig file (default: `~/.kube/config`)
- A StorageClass that supports dynamic provisioning (e.g. `standard`, `gp2`, `premium-rwo`)
- Terraform >= 1.0
## Usage
```bash
# Copy and edit the example variables file
cp terraform.tfvars.example terraform.tfvars
# Deploy
terraform init
terraform plan
terraform apply
```
## Configuration
Two approaches can be combined:
1. **File-based** -- Set `config_json_file` to point to an existing `config.json`.
2. **Variable-based** -- Set individual variables (`config_store`, `logs_store`, `providers_config`). These override matching keys from the file.
See `terraform.tfvars.example` for examples of both.
## Ingress
To expose Bifrost externally, set `create_load_balancer = true` and configure:
- `ingress_class_name` -- Your ingress controller class (e.g. `nginx`, `traefik`, `haproxy`)
- `domain_name` -- The hostname for the Ingress rule
- `ingress_annotations` -- Any annotations your ingress controller needs (e.g. TLS, rate limiting)
## Cleanup
```bash
terraform destroy
```

View File

@@ -0,0 +1,50 @@
terraform {
required_version = ">= 1.0"
required_providers {
kubernetes = {
source = "hashicorp/kubernetes"
version = "~> 2.0"
}
}
}
provider "kubernetes" {
config_path = pathexpand(var.kubeconfig_path)
config_context = var.kubeconfig_context
}
module "bifrost" {
source = "../../modules/bifrost"
cloud_provider = "kubernetes"
service = "deployment"
region = "local"
image_tag = var.image_tag
name_prefix = var.name_prefix
# Config: use a file as base, override with variables
config_json_file = var.config_json_file
# Override specific config sections
config_store = var.config_store
logs_store = var.logs_store
providers_config = var.providers_config
# Compute
desired_count = var.desired_count
cpu = var.cpu
memory = var.memory
kubernetes_namespace = var.kubernetes_namespace
volume_size_gb = var.volume_size_gb
storage_class_name = var.storage_class_name
# Ingress
create_load_balancer = var.create_load_balancer
ingress_class_name = var.ingress_class_name
ingress_annotations = var.ingress_annotations
domain_name = var.domain_name
# Autoscaling
enable_autoscaling = var.enable_autoscaling
min_capacity = var.min_capacity
max_capacity = var.max_capacity
}

View File

@@ -0,0 +1,9 @@
output "service_url" {
description = "URL to access the Bifrost service."
value = module.bifrost.service_url
}
output "health_check_url" {
description = "URL to the Bifrost health check endpoint."
value = module.bifrost.health_check_url
}

View File

@@ -0,0 +1,77 @@
# =============================================================================
# Generic Kubernetes Example — terraform.tfvars
# WARNING: Do NOT commit this file with real secrets (API keys, passwords).
# Use environment variables, a secrets manager, or .gitignore this file.
# =============================================================================
image_tag = "latest"
name_prefix = "bifrost"
# -----------------------------------------------------------------------------
# Kubernetes connection
# -----------------------------------------------------------------------------
# kubeconfig_path = "~/.kube/config"
# kubeconfig_context = "my-cluster"
# -----------------------------------------------------------------------------
# Config approach 1: File-based
# Point to an existing config.json. Variable overrides below will merge on top.
# -----------------------------------------------------------------------------
# config_json_file = "./config.json"
# -----------------------------------------------------------------------------
# Config approach 2: Variable-based
# Define config sections directly. These override matching keys from the file.
# -----------------------------------------------------------------------------
config_store = {
enabled = true
type = "sqlite"
config = {
path = "/app/data/bifrost.db"
}
}
logs_store = {
enabled = true
type = "sqlite"
config = {
path = "/app/data/bifrost-logs.db"
}
}
providers_config = {
openai = {
api_key = "sk-..."
}
anthropic = {
api_key = "sk-ant-..."
}
}
# -----------------------------------------------------------------------------
# Compute
# -----------------------------------------------------------------------------
desired_count = 1
cpu = 512
memory = 1024
kubernetes_namespace = "bifrost"
volume_size_gb = 10
storage_class_name = "standard"
# -----------------------------------------------------------------------------
# Ingress (optional)
# -----------------------------------------------------------------------------
create_load_balancer = false
# ingress_class_name = "nginx"
# ingress_annotations = { "cert-manager.io/cluster-issuer" = "letsencrypt-prod" }
# domain_name = "bifrost.example.com"
# -----------------------------------------------------------------------------
# Autoscaling (optional)
# -----------------------------------------------------------------------------
# NOTE: If you are using OSS version - running multiple nodes has an effect on
# functionality of the system. Please read
# https://docs.getbifrost.ai/deployment-guides/how-to/multinode
enable_autoscaling = false
# min_capacity = 1
# max_capacity = 5

View File

@@ -0,0 +1,139 @@
# --- Kubernetes connection ---
variable "kubeconfig_path" {
description = "Path to the kubeconfig file."
type = string
default = "~/.kube/config"
}
variable "kubeconfig_context" {
description = "Kubeconfig context to use. Defaults to current context."
type = string
default = null
}
# --- Bifrost ---
variable "image_tag" {
description = "Bifrost Docker image tag."
type = string
default = "latest"
}
variable "name_prefix" {
description = "Prefix for all resource names."
type = string
default = "bifrost"
}
# --- Config: file-based ---
variable "config_json_file" {
description = "Path to a Bifrost config.json file. Variables below override matching keys."
type = string
default = null
}
# --- Config: variable-based overrides ---
variable "config_store" {
description = "Config store configuration (type: sqlite/postgres)."
type = any
default = null
}
variable "logs_store" {
description = "Logs store configuration (type: sqlite/postgres)."
type = any
default = null
}
variable "providers_config" {
description = "LLM provider configurations (openai, anthropic, etc.)."
type = any
default = null
}
# --- Compute ---
variable "desired_count" {
description = "Number of pod replicas."
type = number
default = 1
}
variable "cpu" {
description = "CPU allocation in millicores (e.g. 500)."
type = number
default = 512
}
variable "memory" {
description = "Memory allocation in MB."
type = number
default = 1024
}
variable "kubernetes_namespace" {
description = "Kubernetes namespace to deploy into."
type = string
default = "bifrost"
}
variable "volume_size_gb" {
description = "Persistent volume claim size in GB."
type = number
default = 10
}
variable "storage_class_name" {
description = "Kubernetes StorageClass name for dynamic PVC provisioning."
type = string
default = "standard"
}
# --- Ingress ---
variable "create_load_balancer" {
description = "Create a Kubernetes Ingress resource."
type = bool
default = false
}
variable "ingress_class_name" {
description = "Ingress class name (e.g. nginx, traefik, haproxy)."
type = string
default = "nginx"
}
variable "ingress_annotations" {
description = "Annotations to add to the Ingress resource."
type = map(string)
default = {}
}
variable "domain_name" {
description = "Custom domain name for the Ingress host rule."
type = string
default = null
}
# --- Autoscaling ---
variable "enable_autoscaling" {
description = "Enable Horizontal Pod Autoscaler."
type = bool
default = false
}
variable "min_capacity" {
description = "Minimum number of replicas when autoscaling is enabled."
type = number
default = 1
}
variable "max_capacity" {
description = "Maximum number of replicas when autoscaling is enabled."
type = number
default = 10
}