From d589d12a002791b628ccb554ec82f3e7397f1969 Mon Sep 17 00:00:00 2001 From: aries_ckt <916701291@qq.com> Date: Fri, 13 Mar 2026 23:06:04 +0800 Subject: [PATCH] docs: quick-start installation --- README.md | 45 +++- README.zh.md | 35 +++ scripts/install/install.sh | 459 ++++++++++++++++++++++++++++++++ scripts/install/lib/common.sh | 95 +++++++ scripts/install/lib/profiles.sh | 85 ++++++ 5 files changed, 716 insertions(+), 3 deletions(-) create mode 100755 scripts/install/install.sh create mode 100755 scripts/install/lib/common.sh create mode 100755 scripts/install/lib/profiles.sh diff --git a/README.md b/README.md index 79dfbfa67..540fe01ec 100644 --- a/README.md +++ b/README.md @@ -136,19 +136,58 @@ The core capabilities include the following parts: ![agent_prompt_awel_v0 6](https://github.com/user-attachments/assets/40761507-a1e1-49d4-b49a-3dd9a5ea41cc) -## Installation / Quick Start +## Quick Start + +Get DB-GPT running in minutes with the one-line installer (macOS & Linux): + +```bash +curl -fsSL https://raw.githubusercontent.com/eosphoros-ai/DB-GPT/main/scripts/install/install.sh | bash +``` + +Or specify a profile and API key directly: + +```bash +curl -fsSL https://raw.githubusercontent.com/eosphoros-ai/DB-GPT/main/scripts/install/install.sh \ + | OPENAI_API_KEY=sk-xxx bash -s -- --profile openai +``` + +Already have a local DB-GPT checkout? Reuse it instead of cloning `~/.dbgpt/DB-GPT`: + +```bash +OPENAI_API_KEY=sk-xxx \ + bash scripts/install/install.sh --profile openai --repo-dir "$(pwd)" --yes +``` + +After installation, start the server: + +```bash +cd ~/.dbgpt/DB-GPT && uv run dbgpt start webserver --config ~/.dbgpt/configs/openai.toml +``` + +Then open [http://localhost:5670](http://localhost:5670). + +> **Prefer to review the script first?** +> ```bash +> curl -fsSL https://raw.githubusercontent.com/eosphoros-ai/DB-GPT/main/scripts/install/install.sh -o install.sh +> less install.sh +> bash install.sh --profile openai +> ``` + +### Advanced Installation + ![Docker](https://img.shields.io/badge/docker-%230db7ed.svg?style=for-the-badge&logo=docker&logoColor=white) ![Linux](https://img.shields.io/badge/Linux-FCC624?style=for-the-badge&logo=linux&logoColor=black) ![macOS](https://img.shields.io/badge/mac%20os-000000?style=for-the-badge&logo=macos&logoColor=F0F0F0) ![Windows](https://img.shields.io/badge/Windows-0078D6?style=for-the-badge&logo=windows&logoColor=white) -[**Usage Tutorial**](http://docs.dbgpt.cn/docs/overview) +For Docker, local GPU models (vLLM, llama.cpp), or manual source-code setup, see the full docs: + - [**Install**](http://docs.dbgpt.cn/docs/installation) - [Docker](http://docs.dbgpt.cn/docs/installation/docker) - [Source Code](http://docs.dbgpt.cn/docs/installation/sourcecode) - [**Quickstart**](http://docs.dbgpt.cn/docs/quickstart) - [**Application**](http://docs.dbgpt.cn/docs/operation_manual) - - [Development Guide](http://docs.dbgpt.cn/docs/cookbook/app/data_analysis_app_develop) + - [Development Guide](http://docs.dbgpt.cn/docs/cookbook/app/data_analysis_app_develop) - [App Usage](http://docs.dbgpt.cn/docs/application/app_usage) - [AWEL Flow Usage](http://docs.dbgpt.cn/docs/application/awel_flow_usage) - [**Debugging**](http://docs.dbgpt.cn/docs/operation_manual/advanced_tutorial/debugging) diff --git a/README.zh.md b/README.zh.md index cd878c02a..42c93c34a 100644 --- a/README.zh.md +++ b/README.zh.md @@ -140,6 +140,41 @@ ## 安装 +你可以通过一键安装脚本在几分钟内启动 DB-GPT(macOS / Linux): + +```bash +curl -fsSL https://raw.githubusercontent.com/eosphoros-ai/DB-GPT/main/scripts/install/install.sh | bash +``` + +也可以直接指定 profile 和 API Key: + +```bash +curl -fsSL https://raw.githubusercontent.com/eosphoros-ai/DB-GPT/main/scripts/install/install.sh \ + | OPENAI_API_KEY=sk-xxx bash -s -- --profile openai +``` + +如果你已经有本地 DB-GPT 仓库,也可以直接复用当前仓库,跳过 `~/.dbgpt/DB-GPT` 的重复 clone: + +```bash +OPENAI_API_KEY=sk-xxx \ + bash scripts/install/install.sh --profile openai --repo-dir "$(pwd)" --yes +``` + +安装完成后,启动服务: + +```bash +cd ~/.dbgpt/DB-GPT && uv run dbgpt start webserver --config ~/.dbgpt/configs/openai.toml +``` + +然后打开 [http://localhost:5670](http://localhost:5670)。 + +> **想先审阅安装脚本再执行?** +> ```bash +> curl -fsSL https://raw.githubusercontent.com/eosphoros-ai/DB-GPT/main/scripts/install/install.sh -o install.sh +> less install.sh +> bash install.sh --profile openai +> ``` + ![Docker](https://img.shields.io/badge/docker-%230db7ed.svg?style=for-the-badge&logo=docker&logoColor=white) ![Linux](https://img.shields.io/badge/Linux-FCC624?style=for-the-badge&logo=linux&logoColor=black) ![macOS](https://img.shields.io/badge/mac%20os-000000?style=for-the-badge&logo=macos&logoColor=F0F0F0) diff --git a/scripts/install/install.sh b/scripts/install/install.sh new file mode 100755 index 000000000..79e1a4a9c --- /dev/null +++ b/scripts/install/install.sh @@ -0,0 +1,459 @@ +#!/usr/bin/env bash +# ╔════════════════════════════════════════════════════════════════════════════╗ +# ║ DB-GPT Quick Installer ║ +# ║ ║ +# ║ One-line usage: ║ +# ║ curl -fsSL https://raw.githubusercontent.com/eosphoros-ai/DB-GPT/\ ║ +# ║ main/scripts/install/install.sh | bash ║ +# ║ ║ +# ║ What this script does: ║ +# ║ 1. Detect OS (macOS / Linux) ║ +# ║ 2. Ensure git and curl are available ║ +# ║ 3. Install uv (if not already present) ║ +# ║ 4. Clone (or update) the DB-GPT repository ║ +# ║ 5. Run `uv sync` with the extras for the chosen profile ║ +# ║ 6. Generate a user config from template ║ +# ║ 7. Print next-steps (start command, URL) ║ +# ║ ║ +# ║ What this script does NOT do: ║ +# ║ - Install GPU drivers or CUDA ║ +# ║ - Download large local models ║ +# ║ - Modify shell rc files (except via uv installer) ║ +# ║ - Collect telemetry ║ +# ╚════════════════════════════════════════════════════════════════════════════╝ +set -euo pipefail + +# ── Resolve script location (works for both local and curl|bash) ───────────── +# When piped from curl, BASH_SOURCE is empty. In that case we download the +# helper libs from GitHub on the fly. +SCRIPT_DIR="" +REMOTE_BASE="https://raw.githubusercontent.com/eosphoros-ai/DB-GPT/main/scripts/install" + +_resolve_script_dir() { + if [[ -n "${BASH_SOURCE[0]:-}" && "${BASH_SOURCE[0]}" != "bash" ]]; then + SCRIPT_DIR="$(cd -- "$(dirname -- "${BASH_SOURCE[0]}")" && pwd)" + fi +} +_resolve_script_dir + +# ── Source helper libs ──────────────────────────────────────────────────────── +_source_lib() { + local name="$1" + if [[ -n "${SCRIPT_DIR}" && -f "${SCRIPT_DIR}/lib/${name}" ]]; then + # shellcheck source=/dev/null + source "${SCRIPT_DIR}/lib/${name}" + else + # Running via curl | bash — fetch from GitHub + local tmp + tmp="$(mktemp)" + curl -fsSL "${REMOTE_BASE}/lib/${name}" -o "${tmp}" + # shellcheck source=/dev/null + source "${tmp}" + rm -f "${tmp}" + fi +} + +_source_lib "common.sh" +_source_lib "profiles.sh" + +# ── Fetch template file ────────────────────────────────────────────────────── +# Returns the local path to the template. Downloads from GitHub when needed. +_resolve_template() { + local name="$1" + if [[ -n "${SCRIPT_DIR}" && -f "${SCRIPT_DIR}/templates/${name}" ]]; then + echo "${SCRIPT_DIR}/templates/${name}" + else + local tmp + tmp="$(mktemp)" + curl -fsSL "${REMOTE_BASE}/templates/${name}" -o "${tmp}" + echo "${tmp}" + fi +} + +# ── Default values ──────────────────────────────────────────────────────────── +PROFILE="" +INSTALL_DIR="${DBGPT_INSTALL_DIR:-${HOME}/.dbgpt}" +VERSION="${DBGPT_VERSION:-main}" +REPO_DIR="${DBGPT_REPO_DIR:-}" +USE_EXISTING_REPO="false" +MIRROR="" +YES="false" +START_AFTER_INSTALL="false" + +# ── Usage ───────────────────────────────────────────────────────────────────── +usage() { + cat <<'EOF' +DB-GPT Quick Installer + +Usage: + install.sh [options] + +Options: + --profile Deployment profile (currently: openai) + --install-dir Where to install (default: ~/.dbgpt) + --version Git tag or branch to check out (default: main) + --repo-dir Use an existing local DB-GPT checkout + --mirror china Use China PyPI mirror (Tsinghua) + --yes Non-interactive — accept all defaults + --start Start DB-GPT server after install + -h, --help Show this help + +Environment variables: + OPENAI_API_KEY Automatically injected into OpenAI config + DBGPT_INSTALL_DIR Override default install directory + DBGPT_REPO_DIR Reuse an existing local DB-GPT repo + DBGPT_VERSION Override default git ref + +Examples: + # Interactive (will ask which profile) + bash install.sh + + # Fully non-interactive + bash install.sh --profile openai --yes + + # With API key + OPENAI_API_KEY=sk-xxx bash install.sh --profile openai --yes + + # Reuse your current local repo (skip clone/update) + OPENAI_API_KEY=sk-xxx bash install.sh --profile openai --repo-dir . --yes + + # China mirror + bash install.sh --profile openai --mirror china +EOF +} + +# ── Argument parsing ────────────────────────────────────────────────────────── +parse_args() { + while [[ $# -gt 0 ]]; do + case "$1" in + --profile) + PROFILE="${2:-}" + [[ -z "${PROFILE}" ]] && die "--profile requires a value" + shift 2 + ;; + --install-dir) + INSTALL_DIR="${2:-}" + [[ -z "${INSTALL_DIR}" ]] && die "--install-dir requires a value" + shift 2 + ;; + --version) + VERSION="${2:-}" + [[ -z "${VERSION}" ]] && die "--version requires a value" + shift 2 + ;; + --repo-dir) + REPO_DIR="${2:-}" + [[ -z "${REPO_DIR}" ]] && die "--repo-dir requires a value" + shift 2 + ;; + --mirror) + MIRROR="${2:-}" + [[ -z "${MIRROR}" ]] && die "--mirror requires a value" + shift 2 + ;; + --yes) + YES="true" + shift + ;; + --start) + START_AFTER_INSTALL="true" + shift + ;; + -h|--help) + usage + exit 0 + ;; + *) + die "Unknown argument: $1. Run with --help for usage." + ;; + esac + done +} + +# ── Steps ───────────────────────────────────────────────────────────────────── + +step_check_platform() { + local os arch + os="$(uname -s)" + arch="$(uname -m)" + + case "${os}" in + Darwin|Linux) ;; + *) + die "Unsupported OS: ${os}. This installer supports macOS and Linux." + ;; + esac + + info "Platform: ${os} ${arch}" +} + +step_ensure_base_commands() { + require_cmd curl + require_cmd git +} + +step_choose_profile() { + if [[ -n "${PROFILE}" ]]; then + return + fi + + if [[ "${YES}" == "true" ]]; then + PROFILE="openai" + info "Non-interactive mode: defaulting to profile 'openai'" + return + fi + + printf '\n' + printf '%b' "${COLOR_CYAN}Select a deployment profile:${COLOR_RESET}\n" + printf ' 1) openai — OpenAI API proxy (recommended)\n' + printf ' q) quit\n' + printf '\n' + + local choice + read -r -p "Enter choice [1]: " choice + choice="${choice:-1}" + + case "${choice}" in + 1|openai) PROFILE="openai" ;; + q|Q) info "Installation cancelled."; exit 0 ;; + *) die "Invalid choice: ${choice}" ;; + esac +} + +step_ensure_uv() { + if command -v uv >/dev/null 2>&1; then + success "uv found: $(uv --version 2>/dev/null || echo 'unknown')" + return + fi + + info "uv not found. Installing..." + curl -LsSf https://astral.sh/uv/install.sh | sh + + # uv installer puts the binary in ~/.local/bin or ~/.cargo/bin. + # Try to pick it up without requiring the user to reload their shell. + for candidate in \ + "${HOME}/.local/bin" \ + "${HOME}/.cargo/bin" + do + if [[ -x "${candidate}/uv" ]]; then + export PATH="${candidate}:${PATH}" + break + fi + done + + if ! command -v uv >/dev/null 2>&1; then + die "uv was installed but cannot be found on PATH. Please open a new terminal and re-run." + fi + + success "uv installed: $(uv --version 2>/dev/null || echo 'unknown')" +} + +step_apply_mirror() { + if [[ "${MIRROR}" == "china" ]]; then + export UV_INDEX_URL="https://pypi.tuna.tsinghua.edu.cn/simple" + info "China mirror enabled: UV_INDEX_URL=${UV_INDEX_URL}" + fi +} + +step_prepare_dirs() { + mkdir -p "${INSTALL_DIR}/configs" +} + +resolve_repo_dir() { + if [[ -z "${REPO_DIR}" ]]; then + REPO_DIR="${INSTALL_DIR}/DB-GPT" + return + fi + + USE_EXISTING_REPO="true" + + [[ -d "${REPO_DIR}" ]] || die "--repo-dir does not exist: ${REPO_DIR}" + + local resolved_repo_dir + resolved_repo_dir="$(git -C "${REPO_DIR}" rev-parse --show-toplevel 2>/dev/null)" \ + || die "--repo-dir must point to a DB-GPT git checkout: ${REPO_DIR}" + + REPO_DIR="${resolved_repo_dir}" + + if [[ "${VERSION}" != "main" ]]; then + warn "--version is ignored when --repo-dir is set. Using existing checkout at ${REPO_DIR}." + fi +} + +step_clone_or_update_repo() { + local repo_dir="${REPO_DIR}" + + if [[ "${USE_EXISTING_REPO}" == "true" ]]; then + info "Using existing local repo: ${repo_dir}" + return + fi + + if [[ ! -e "${repo_dir}" ]]; then + run "Cloning DB-GPT repository..." \ + git clone --depth 1 --branch "${VERSION}" \ + https://github.com/eosphoros-ai/DB-GPT.git "${repo_dir}" + return + fi + + if [[ ! -d "${repo_dir}/.git" ]]; then + die "Directory exists but is not a git repo: ${repo_dir}. Remove it and re-run." + fi + + info "Existing DB-GPT repo found: ${repo_dir}" + if confirm "Update to version '${VERSION}'?"; then + run "Fetching latest..." git -C "${repo_dir}" fetch --tags --prune + run "Checking out ${VERSION}..." git -C "${repo_dir}" checkout "${VERSION}" + else + info "Skipping repo update." + fi +} + +step_install_deps() { + local repo_dir="${REPO_DIR}" + local extras + extras="$(profile_extras "${PROFILE}")" + + info "Installing dependencies for profile: ${PROFILE}" + + local extra_args=() + while IFS= read -r extra; do + [[ -z "${extra}" ]] && continue + extra_args+=(--extra "${extra}") + done <<< "${extras}" + + ( + cd "${repo_dir}" + run "Running uv sync (this may take a few minutes)..." \ + uv sync --all-packages "${extra_args[@]}" + ) + + success "Dependencies installed." +} + +step_generate_config() { + local template_name + template_name="$(profile_template "${PROFILE}")" + + local template_path + template_path="$(_resolve_template "${template_name}")" + + local target_path="${INSTALL_DIR}/configs/${template_name}" + + if [[ -f "${target_path}" ]]; then + if ! confirm "Config already exists: ${target_path}. Overwrite?"; then + info "Keeping existing config." + return + fi + fi + + cp "${template_path}" "${target_path}" + + # Inject API key from environment if available + local api_key_env api_key_token + api_key_env="$(profile_api_key_env "${PROFILE}")" + api_key_token="$(profile_api_key_token "${PROFILE}")" + + if [[ -n "${api_key_env}" && -n "${api_key_token}" ]]; then + local api_key_value="${!api_key_env:-}" + if [[ -n "${api_key_value}" ]]; then + replace_token "${target_path}" "${api_key_token}" "${api_key_value}" + success "API key injected from \$${api_key_env}." + else + warn "\$${api_key_env} is not set. Please edit ${target_path} and fill in your API key before starting." + fi + fi +} + +step_validate() { + local repo_dir="${REPO_DIR}" + + ( + cd "${repo_dir}" + if uv run dbgpt --version >/dev/null 2>&1; then + success "dbgpt CLI verified: $(uv run dbgpt --version 2>/dev/null || echo 'ok')" + else + warn "Could not verify dbgpt CLI. This may be fine — try starting the server." + fi + ) +} + +step_print_summary() { + local repo_dir="${REPO_DIR}" + local template_name + template_name="$(profile_template "${PROFILE}")" + local config_path="${INSTALL_DIR}/configs/${template_name}" + + printf '%b' " +${COLOR_GREEN}════════════════════════════════════════════════════════════${COLOR_RESET} +${COLOR_GREEN} DB-GPT installed successfully!${COLOR_RESET} +${COLOR_GREEN}════════════════════════════════════════════════════════════${COLOR_RESET} + + Profile: ${PROFILE} + Repository: ${repo_dir} + Config: ${config_path} + + ${COLOR_CYAN}Next steps:${COLOR_RESET} + + 1. Review / edit your config (set API key if not done): + ${COLOR_YELLOW}${config_path}${COLOR_RESET} + + 2. Start DB-GPT: + ${COLOR_YELLOW}cd \"${repo_dir}\" && uv run dbgpt start webserver --config \"${config_path}\"${COLOR_RESET} + + 3. Open your browser: + ${COLOR_YELLOW}http://localhost:5670${COLOR_RESET} + +" +} + +step_start_if_requested() { + if [[ "${START_AFTER_INSTALL}" != "true" ]]; then + return + fi + + local repo_dir="${REPO_DIR}" + local template_name + template_name="$(profile_template "${PROFILE}")" + local config_path="${INSTALL_DIR}/configs/${template_name}" + + info "Starting DB-GPT server..." + ( + cd "${repo_dir}" + exec uv run dbgpt start webserver --config "${config_path}" + ) +} + +# ── Main ────────────────────────────────────────────────────────────────────── +main() { + printf '%b' "${COLOR_GREEN}" + cat <<'BANNER' + + ____ ____ ____ ____ _____ + | _ \| __ ) / ___| _ \_ _| + | | | | _ \ ____| | _| |_) || | + | |_| | |_) |____| |_| | __/ | | + |____/|____/ \____|_| |_| + + Quick Installer + +BANNER + printf '%b' "${COLOR_RESET}" + + parse_args "$@" + step_check_platform + step_ensure_base_commands + step_choose_profile + validate_profile "${PROFILE}" + step_apply_mirror + step_prepare_dirs + resolve_repo_dir + step_ensure_uv + step_clone_or_update_repo + step_install_deps + step_generate_config + step_validate + step_print_summary + step_start_if_requested +} + +main "$@" diff --git a/scripts/install/lib/common.sh b/scripts/install/lib/common.sh new file mode 100755 index 000000000..5f69be829 --- /dev/null +++ b/scripts/install/lib/common.sh @@ -0,0 +1,95 @@ +#!/usr/bin/env bash +# common.sh - Shared utility functions for DB-GPT installer +# shellcheck disable=SC2034 + +# ── Colors ──────────────────────────────────────────────────────────────────── +readonly COLOR_RESET='\033[0m' +readonly COLOR_RED='\033[1;31m' +readonly COLOR_GREEN='\033[1;32m' +readonly COLOR_YELLOW='\033[1;33m' +readonly COLOR_BLUE='\033[1;34m' +readonly COLOR_CYAN='\033[1;36m' + +# ── Logging ─────────────────────────────────────────────────────────────────── +info() { + printf "${COLOR_BLUE}[INFO]${COLOR_RESET} %s\n" "$*" +} + +warn() { + printf "${COLOR_YELLOW}[WARN]${COLOR_RESET} %s\n" "$*" +} + +error() { + printf "${COLOR_RED}[ERROR]${COLOR_RESET} %s\n" "$*" >&2 +} + +success() { + printf "${COLOR_GREEN}[OK]${COLOR_RESET} %s\n" "$*" +} + +die() { + error "$*" + exit 1 +} + +# ── Command helpers ─────────────────────────────────────────────────────────── + +# Check that a command exists, die if not. +require_cmd() { + local cmd="$1" + if ! command -v "${cmd}" >/dev/null 2>&1; then + die "Required command not found: ${cmd}. Please install it first." + fi +} + +# Run a command with a description printed before it. +run() { + local desc="$1" + shift + info "${desc}" + if ! "$@"; then + die "Command failed: $*" + fi +} + +# ── Interactive helpers ─────────────────────────────────────────────────────── + +# Ask a yes/no question. Respects the global YES flag for non-interactive use. +confirm() { + local prompt="$1" + + if [[ "${YES:-false}" == "true" ]]; then + return 0 + fi + + local answer + read -r -p "${prompt} [y/N]: " answer + [[ "${answer}" =~ ^[Yy]$ ]] +} + +# ── String helpers ──────────────────────────────────────────────────────────── + +# Replace a placeholder token inside a file with a real value. +# Usage: replace_token +# Example: replace_token config.toml "__OPENAI_API_KEY__" "sk-xxx" +replace_token() { + local file="$1" + local token="$2" + local value="$3" + + if [[ ! -f "${file}" ]]; then + die "replace_token: file not found: ${file}" + fi + + # Use python3 for safe in-place replacement (avoids sed portability issues + # between macOS and Linux). We pass values through environment variables to + # avoid shell-injection via triple-quote escapes. + _RT_FILE="${file}" _RT_TOKEN="${token}" _RT_VALUE="${value}" python3 -c " +import os +from pathlib import Path +p = Path(os.environ['_RT_FILE']) +text = p.read_text() +text = text.replace(os.environ['_RT_TOKEN'], os.environ['_RT_VALUE']) +p.write_text(text) +" +} diff --git a/scripts/install/lib/profiles.sh b/scripts/install/lib/profiles.sh new file mode 100755 index 000000000..920f041e8 --- /dev/null +++ b/scripts/install/lib/profiles.sh @@ -0,0 +1,85 @@ +#!/usr/bin/env bash +# profiles.sh - Profile definitions for DB-GPT installer +# +# Each profile maps to: +# 1. A set of uv extras (fed to `uv sync --extra ...`) +# 2. A config template under templates/ +# 3. The official config file path in the repo (for reference) + +# ── Validation ──────────────────────────────────────────────────────────────── + +# Currently supported profiles. Extend this list when adding new profiles. +readonly SUPPORTED_PROFILES="openai" + +validate_profile() { + local profile="$1" + case "${profile}" in + openai) ;; + *) + die "Unsupported profile: ${profile}. Supported profiles: ${SUPPORTED_PROFILES}" + ;; + esac +} + +# ── Extras mapping ──────────────────────────────────────────────────────────── +# Returns newline-separated extras for the given profile. +# These are taken directly from install_help.py / get_deployment_presets(). + +profile_extras() { + local profile="$1" + case "${profile}" in + openai) + cat <<'EOF' +base +proxy_openai +rag +storage_chromadb +dbgpts +EOF + ;; + *) + die "No extras defined for profile: ${profile}" + ;; + esac +} + +# ── Config template name ────────────────────────────────────────────────────── +# Returns the template filename (relative to templates/ dir). + +profile_template() { + local profile="$1" + case "${profile}" in + openai) echo "openai.toml" ;; + *) die "No template defined for profile: ${profile}" ;; + esac +} + +# ── Repo config path (for display / fallback) ──────────────────────────────── + +profile_repo_config() { + local profile="$1" + case "${profile}" in + openai) echo "configs/dbgpt-proxy-openai.toml" ;; + *) die "No repo config path defined for profile: ${profile}" ;; + esac +} + +# ── Environment variable name for API key ───────────────────────────────────── + +profile_api_key_env() { + local profile="$1" + case "${profile}" in + openai) echo "OPENAI_API_KEY" ;; + *) echo "" ;; + esac +} + +# ── Placeholder token in config template ────────────────────────────────────── + +profile_api_key_token() { + local profile="$1" + case "${profile}" in + openai) echo "__OPENAI_API_KEY__" ;; + *) echo "" ;; + esac +}