Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
38 changes: 38 additions & 0 deletions frontend/.env.example
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
# Trivela Frontend Environment Variables
# Copy this file to .env.local and fill in your values.
# Environment presets: development | staging | production
# VITE_ENV determines which preset is used as the default.
# Individual VITE_* variables override the preset values.

# ── Environment preset ────────────────────────────────────────────────────────
# Set to "development", "staging", or "production".
# Each preset provides default values for all URLs and contract IDs below.
VITE_ENV=development

# ── Backend API ───────────────────────────────────────────────────────────────
# The base URL of the Trivela backend API (no trailing slash).
# Development: http://localhost:3001
# Staging: https://trivela-api-staging.example.com
# Production: https://trivela-api.example.com
VITE_API_URL=http://localhost:3001

# ── Stellar network ───────────────────────────────────────────────────────────
#Soroban RPC endpoint (testnet or mainnet).
VITE_SOROBAN_RPC_URL=https://soroban-testnet.stellar.org

# Horizon API endpoint for account data.
VITE_HORIZON_URL=https://horizon-testnet.stellar.org

# Stellar network passphrase. Use "Test SDF Network ; September 2015" for testnet.
# Mainnet passphrase is "Public Global Stellar Network ; September 2015"
VITE_STELLAR_NETWORK_PASSPHRASE="Test SDF Network ; September 2015"

# ── Contract IDs ──────────────────────────────────────────────────────────────
# Contract IDs are obtained after deploying the contracts with:
# stellar contract deploy --source <ACCOUNT> --network testnet --wasm contracts/rewards/target/wasm32-unknown-unknown/release/rewards.wasm

# Rewards contract ID (manages user points balances)
VITE_REWARDS_CONTRACT_ID=

# Campaign contract ID (manages campaign creation and participant registration)
VITE_CAMPAIGN_CONTRACT_ID=
117 changes: 117 additions & 0 deletions frontend/src/config.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,117 @@
/**
* Environment-based configuration for Trivela frontend.
*
* Usage: Set VITE_ENV to "development", "staging", or "production".
* Individual VITE_* variables can still be used to override any preset value.
*
* Example .env.development:
* VITE_ENV=development
* VITE_API_URL=http://localhost:3001
*
* Example .env.staging:
* VITE_ENV=staging
* VITE_API_URL=https://trivela-api-staging.example.com
*
* Example .env.production:
* VITE_ENV=production
* VITE_API_URL=https://trivela-api.example.com
*/

import { Networks } from "@stellar/stellar-sdk";

/** @type {Record<string, {stellar: {networkPassphrase: string, sorobanRpcUrl: string, horizonUrl: string}, contracts: {rewardsContractId: string, campaignContractId: string}, apiUrl: string}>} */
const ENV_PRESETS = {
development: {
stellar: {
networkPassphrase: Networks.TESTNET,
sorobanRpcUrl: "https://soroban-testnet.stellar.org",
horizonUrl: "https://horizon-testnet.stellar.org",
},
contracts: {
rewardsContractId: "",
campaignContractId: "",
},
apiUrl: "http://localhost:3001",
},
staging: {
stellar: {
networkPassphrase: Networks.TESTNET,
sorobanRpcUrl: "https://soroban-testnet.stellar.org",
horizonUrl: "https://horizon-testnet.stellar.org",
},
contracts: {
rewardsContractId: "",
campaignContractId: "",
},
apiUrl: "",
},
production: {
stellar: {
networkPassphrase: Networks.MAINNET,
sorobanRpcUrl: "https://soroban.mainnet.stellar.org",
horizonUrl: "https://horizon.stellar.org",
},
contracts: {
rewardsContractId: "",
campaignContractId: "",
},
apiUrl: "",
},
};

/**
* Resolve a single config value.
* Priority: explicit env var > preset value
*
* @template T
* @param {T} presetValue
* @param {string} envKey - VITE_ prefix is added automatically
* @returns {T}
*/
function resolve(presetValue, envKey) {
const envVal = import.meta.env[envKey];
if (typeof envVal === "string" && envVal.trim() !== "") {
return envVal;
}
return presetValue;
}

function resolveContractId(presetValue, envKey) {
return resolve(presetValue, envKey);
}

const presetKey = /** @type {keyof typeof ENV_PRESETS} */ (
import.meta.env.VITE_ENV || "development"
);
const preset = ENV_PRESETS[presetKey] ?? ENV_PRESETS.development;

export const STELLAR_NETWORK_PASSPHRASE = resolve(
preset.stellar.networkPassphrase,
"VITE_STELLAR_NETWORK_PASSPHRASE"
);

export const SOROBAN_RPC_URL = resolve(
preset.stellar.sorobanRpcUrl,
"VITE_SOROBAN_RPC_URL"
);

export const HORIZON_URL = resolve(
preset.stellar.horizonUrl,
"VITE_HORIZON_URL"
);

export const REWARDS_CONTRACT_ID = resolveContractId(
preset.contracts.rewardsContractId,
"VITE_REWARDS_CONTRACT_ID"
);

export const CAMPAIGN_CONTRACT_ID = resolveContractId(
preset.contracts.campaignContractId,
"VITE_CAMPAIGN_CONTRACT_ID"
);

/** Backend API base URL (no trailing slash). */
export const API_URL = resolve(preset.apiUrl, "VITE_API_URL");

/** Current environment name, one of "development", "staging", "production". */
export const ENV_NAME = presetKey;
21 changes: 7 additions & 14 deletions frontend/src/stellar.js
Original file line number Diff line number Diff line change
Expand Up @@ -18,20 +18,13 @@ import {

/* ---------- environment configuration ---------- */

export const SOROBAN_RPC_URL =
import.meta.env.VITE_SOROBAN_RPC_URL || "https://soroban-testnet.stellar.org";

export const REWARDS_CONTRACT_ID =
import.meta.env.VITE_REWARDS_CONTRACT_ID || "";

export const CAMPAIGN_CONTRACT_ID =
import.meta.env.VITE_CAMPAIGN_CONTRACT_ID || "";

export const NETWORK_PASSPHRASE =
import.meta.env.VITE_STELLAR_NETWORK_PASSPHRASE || Networks.TESTNET;

export const HORIZON_URL =
import.meta.env.VITE_HORIZON_URL || "https://horizon-testnet.stellar.org";
import {
SOROBAN_RPC_URL,
REWARDS_CONTRACT_ID,
CAMPAIGN_CONTRACT_ID,
NETWORK_PASSPHRASE,
HORIZON_URL,
} from "./config";

/* ---------- Freighter helpers ---------- */

Expand Down