Live site: constancehairart.com
Private production repository for Constance's Hair Art — a premium African hair salon in Stavanger, Norway.
Developed by TheRealOdinEYE
Public open-source template (no credentials): afro-hair-salon-website
| Layer | Technology |
|---|---|
| Framework | Next.js 14 (App Router) |
| Language | TypeScript |
| Styling | Tailwind CSS |
| Database | SQLite via Prisma 7 |
| Auth | NextAuth.js v4 |
| AI Chatbot | Google Gemini 2.0 Flash |
| Human Handoff | Telegram Bot API |
| Nodemailer (Gmail SMTP) | |
| Calendar | Google Calendar API |
| Container | Docker + Docker Compose |
- AI chatbot (Norwegian + English auto-detect) with human handoff to Telegram
- Online booking system with email confirmations
- Google Calendar two-way sync
- Instagram feed integration
- Admin panel at
/admin - RAG knowledge base (markdown files in
/data) - Rate limiting, security headers, httpOnly session cookies
# Build and start
docker compose up -d --build
# Restart without rebuild
docker compose restart
# View logs
docker logs hair-art -fSite runs on port 8081.
All credentials are in .env (gitignored — never committed).
Copy .env.example for reference on required variables.
Register once after deploy or domain change:
curl -X POST "https://api.telegram.org/bot<TOKEN>/setWebhook" \
-d "url=https://constancehairart.com/api/chat/telegram-webhook" \
-d "secret_token=<TELEGRAM_WEBHOOK_SECRET>" \
-d "allowed_updates=[\"message\"]"Reply to customers from Telegram:
/reply <session-id-8-chars> Your message here
Edit markdown files in /data — no code changes needed:
| File | Contents |
|---|---|
data/services.md |
Services and descriptions |
data/prices.md |
Pricing table |
data/faq.md |
FAQ (Norwegian + English) |
data/opening_hours.md |
Hours and booking policy |
data/contact.md |
Address and directions |
Apply changes without full rebuild:
docker cp data/services.md hair-art:/app/data/services.mdURL: /admin
Change password immediately after first login.
npm install
cp .env.example .env # fill in values
npx prisma migrate dev
npm run db:seed
npm run devMIT © TheRealOdinEYE