Skip to content

Checking access...

FAS Local Setup Guide

This guide covers setting up the Frontend Application Split repositories for local development.

Table of Contents

Prerequisites

  • Node.js 20+ and npm 9+
  • Git
  • GitHub account with access to the Hello-World-Co-Op organization
  • dfx CLI (optional, only needed for IC canister deployment)

Quick Start: Run a Single Suite

The fastest way to get started is running one suite locally.

1. Configure GitHub Packages Authentication

Create a GitHub Personal Access Token (PAT) with read:packages scope, then configure npm:

bash
# Create/edit ~/.npmrc (global npm config)
echo "@hello-world-co-op:registry=https://npm.pkg.github.com" >> ~/.npmrc
echo "//npm.pkg.github.com/:_authToken=YOUR_GITHUB_PAT" >> ~/.npmrc

Replace YOUR_GITHUB_PAT with your actual token.

Note: The scope MUST be @hello-world-co-op (matching the GitHub org name Hello-World-Co-Op). Using @helloworlddao will fail.

2. Clone and Run a Suite

Pick any suite and get it running:

bash
git clone https://github.com/Hello-World-Co-Op/<suite-name>.git
cd <suite-name>
cp .env.example .env.local
# Edit .env.local with canister IDs (see Environment Variables below)
npm install
npm run dev

Default ports:

SuitePortURL
marketing-suite5173http://localhost:5173
think-tank-suite5174http://localhost:5174
governance-suite5174http://localhost:5174
dao-suite5174http://localhost:5174
otter-camp-suite5176http://localhost:5176
dao-admin-suite5176http://localhost:5176

3. Run Tests

bash
# Unit tests
npm test

# TypeScript check
npx tsc --noEmit

# Lint
npm run lint

# E2E tests (if available)
npm run test:e2e

Suite-Specific Local Development

marketing-suite (Standalone)

The marketing suite is the simplest to run -- no auth or oracle-bridge needed.

bash
cd ~/git/marketing-suite
npm install
npm run dev        # Dev server on http://localhost:5173

Build with SEO pre-rendering:

bash
npm run build      # Runs: tsc + vite build + prerender + sitemap generation

Pre-rendered HTML files are generated in dist/ along with sitemap.xml. Build time includes ~30s for pre-rendering (expected).

Key files:

  • src/entry-prerender.tsx -- SSR entry point (add new routes here)
  • scripts/prerender.ts -- Build-time HTML generation
  • scripts/generate-sitemap.ts -- Sitemap generation (add new routes here)

otter-camp-suite (Standalone)

The game suite is standalone but has specific Phaser.js requirements.

bash
cd ~/git/otter-camp-suite
npm install
npm run dev        # Dev server on http://localhost:5176
# Navigate to /otter-camp to load the game

Optional -- Multiplayer: To enable real-time multiplayer presence, start oracle-bridge:

bash
cd ~/git/oracle-bridge
npm run dev        # WebSocket server on http://localhost:3000

The game gracefully degrades to single-player mode if oracle-bridge is unavailable.

Key environment variables:

bash
VITE_WS_URL=ws://localhost:3000     # WebSocket for multiplayer
VITE_IC_HOST=http://127.0.0.1:4943  # IC host (optional, no canister calls in game)

dao-suite (Auth-Integrated)

The dao-suite requires oracle-bridge for authentication.

bash
# 1. Start oracle-bridge (required for auth)
cd ~/git/oracle-bridge
npm run dev        # http://localhost:3000

# 2. Start dao-suite
cd ~/git/dao-suite
cp .env.example .env.local
# Edit .env.local:
#   VITE_ORACLE_BRIDGE_URL=http://localhost:3000
#   VITE_THINK_TANK_URL=http://localhost:5174
npm install
npm run dev        # http://localhost:5174

# Alternative: bypass auth for local development
npm run dev:qa     # Sets VITE_DEV_AUTH_BYPASS=true

Auth flow: Unauthenticated users are redirected to VITE_THINK_TANK_URL for login. After login, they are redirected back with a session cookie.

dao-admin-suite (Auth-Integrated + RBAC)

Same as dao-suite, plus AdminGuard for admin-only routes.

bash
# 1. Start oracle-bridge (required for auth)
cd ~/git/oracle-bridge
npm run dev

# 2. Start dao-admin-suite
cd ~/git/dao-admin-suite
cp .env.example .env.local
# Edit .env.local (same as dao-suite)
npm install
npm run dev        # http://localhost:5176

# Alternative: bypass auth for local development
npm run dev:qa     # Sets VITE_DEV_AUTH_BYPASS=true

Note: dev:qa mode bypasses AdminGuard locally. In staging/production, AdminGuard enforces role-based access.

think-tank-suite and governance-suite

These suites were migrated in FAS-3 and follow the same setup pattern:

bash
cd ~/git/<suite-name>
npm install
cp .env.example .env.local
# Edit .env.local with canister IDs
npm run dev

For QA testing without authentication:

bash
npm run dev:qa     # Sets VITE_DEV_AUTH_BYPASS=true

Oracle-Bridge Local Setup

The oracle-bridge is required for auth-integrated suites (think-tank, governance, dao, dao-admin).

Running oracle-bridge locally

bash
cd ~/git/oracle-bridge
npm install
npm run dev        # Starts on http://localhost:3000

Verify oracle-bridge is running

bash
curl http://localhost:3000/health
# Expected: {"status":"ok"}

Configure suites to use local oracle-bridge

In each auth-integrated suite's .env.local:

bash
VITE_ORACLE_BRIDGE_URL=http://localhost:3000

For staging, use:

bash
VITE_ORACLE_BRIDGE_URL=https://staging-oracle.helloworlddao.com

Common oracle-bridge issues

IssueCauseFix
ECONNREFUSED on port 3000oracle-bridge not runningStart with npm run dev
ERR_ERL_KEY_GEN_IPV6express-rate-limit IPv6 validationFixed in FAS-8.1 -- pull latest
CORS errorsMissing origin in oracle-bridge configAdd http://localhost:5174 to allowed origins

Environment Variables

Each suite requires environment variables for canister IDs and service URLs. Copy .env.example to .env.local and configure:

Common Variables

VariableDescriptionExample
VITE_IC_HOSTIC network hosthttps://ic0.app or http://localhost:4943
VITE_AUTH_SERVICE_CANISTER_IDauth-service canistergexqh-jqaaa-aaaae-acsxq-cai
VITE_USER_SERVICE_CANISTER_IDuser-service canisterj4rvr-3aaaa-aaaao-qkvfq-cai

Auth-Integrated Suite Variables

VariableDescriptionExample
VITE_ORACLE_BRIDGE_URLOracle-bridge URLhttp://localhost:3000
VITE_THINK_TANK_URLThink Tank URL (login redirect)http://localhost:5174
VITE_DEV_AUTH_BYPASSSkip auth in dev modetrue (dev only)

Suite-Specific Variables

See each suite's .env.example for the complete list of required variables.

Package Development: Cross-Package Changes

When you need to modify a shared package and test it in a suite simultaneously, use the npm link workflow.

bash
# 1. Clone the package you want to modify
git clone https://github.com/Hello-World-Co-Op/ui.git
cd ui
npm install
npm run build

# 2. Create a global link
npm link

# 3. In your suite, link to the local package
cd ../think-tank-suite
npm link @hello-world-co-op/ui

# 4. Make changes to ui, rebuild, and they appear in the suite
cd ../ui
# ... edit files ...
npm run build
# Changes are immediately available in think-tank-suite

file: References (Alternative)

For rapid iteration, you can use file: references in package.json:

json
{
  "dependencies": {
    "@hello-world-co-op/ui": "file:../ui"
  }
}

Then run npm install to create the symlink.

Warning: Do NOT commit file: references. The package-publish.yml workflow detects stale file: references in package-lock.json and falls back to npm install to avoid broken symlinks in CI.

Full Local Dev Workflow Documentation

For the complete cross-package development guide including multi-package chains, IDE integration, and troubleshooting, see the Local Development Workflow section in the dot-github README.

Full Stack: Suite + IC Canisters

To run a suite with real canister backends:

Option A: Against Staging Canisters

Use the staging canister IDs in your .env.local:

bash
VITE_IC_HOST=https://ic0.app
VITE_AUTH_SERVICE_CANISTER_ID=gexqh-jqaaa-aaaae-acsxq-cai
# ... other staging canister IDs from .env.example

Option B: Against Local PocketIC

Requires the full local dev environment setup:

bash
dfx start --background
dfx deploy          # Deploys all canisters

Repository Clone Locations

By convention, all repos live under ~/git/:

~/git/
├── hello-world-workspace/   # VS Code workspace
├── docs/                    # Documentation
├── api/                     # @hello-world-co-op/api
├── auth/                    # @hello-world-co-op/auth
├── ui/                      # @hello-world-co-op/ui
├── suite-template/          # Suite template
├── think-tank-suite/       # Think Tank app
├── governance-suite/        # Governance app
├── marketing-suite/         # Marketing site (standalone)
├── otter-camp-suite/        # Otter Camp game (standalone)
├── dao-suite/               # DAO member dashboard
├── dao-admin-suite/         # DAO admin dashboard
├── oracle-bridge/           # Off-chain auth proxy
├── dot-github/              # .github org repo (reusable workflows)
└── ...                      # Backend canister repos

Suite-Specific Troubleshooting

marketing-suite: SEO pre-rendering build time

Issue: npm run build takes > 60 seconds. Cause: Pre-rendering all routes with ReactDOMServer.renderToString() is slow. Fix: This is expected (~30s for pre-rendering). If adding many routes, use selective pre-rendering (only pre-render SEO-critical pages).

otter-camp-suite: Phaser.js not loading

Issue: Game canvas does not render, black screen. Cause: Phaser.AUTO configuration issue or missing game assets. Fix:

  1. Check browser console for Phaser errors
  2. Verify Phaser.AUTO mode is set in game config
  3. Check that game assets exist in public/assets/
  4. Navigate to /otter-camp (not root /)

dao-suite / dao-admin-suite: Oracle-bridge connection refused

Issue: ECONNREFUSED 127.0.0.1:3000 errors. Cause: oracle-bridge is not running locally. Fix:

  1. Start oracle-bridge: cd ~/git/oracle-bridge && npm run dev
  2. Verify: curl http://localhost:3000/health
  3. Check VITE_ORACLE_BRIDGE_URL in .env.local is http://localhost:3000
  4. Alternative: use npm run dev:qa to bypass auth entirely

Staging Deployment Pre-Flight Checklist

Before deploying a service to staging for the first time (especially oracle-bridge or new suite integrations), verify each item. This checklist was created after FAS-8.1 discovered 5 simultaneous bugs during the first oracle-bridge staging deployment.

Environment Variables

  • [ ] All required env vars are set in the staging deployment config
  • [ ] AUTH_SERVICE_CANISTER_ID is correct for staging
  • [ ] AUTH_COOKIE_DOMAIN is set to .helloworlddao.com
  • [ ] AUTH_COOKIE_SECURE=true and AUTH_COOKIE_SAME_SITE=lax
  • [ ] VITE_ORACLE_BRIDGE_URL points to the staging oracle-bridge URL
  • [ ] VITE_THINK_TANK_URL points to https://staging-think-tank.helloworlddao.com

Source Files

  • [ ] All source files are included in the deployment (no missing modules)
  • [ ] No local-only files accidentally excluded from git
  • [ ] Build output (dist/) is complete and includes all routes

Canister Health

  • [ ] Target canister is in Running state: dfx canister status <id> --network ic
  • [ ] Canister has sufficient cycles (minimum 2 TC buffer)
  • [ ] Dependent canisters (auth-service, user-service) also have sufficient cycles
  • [ ] Inter-canister call targets are registered (e.g., authorized_canisters list)

Dependencies

  • [ ] All npm dependencies installed (no missing packages)
  • [ ] No file: references in package-lock.json (breaks CI)
  • [ ] @dfinity/agent version matches across packages

Suite-Specific (.env.staging)

  • [ ] .env.staging file exists for auth-integrated suites (dao-suite, dao-admin-suite)
  • [ ] All VITE_* variables are set (they are baked in at build time)
  • [ ] Build with staging env: verify VITE_ORACLE_BRIDGE_URL is not empty

Post-Deploy Verification

  • [ ] Health check endpoint returns OK: curl https://<service-url>/health
  • [ ] Browser test: navigate to staging URL, verify rendering
  • [ ] Auth flow: login → session check → logout → session check
  • [ ] No console errors in browser DevTools

Hello World Co-Op DAO