Kenneth Andales' chatbot API. Streaming responses, live data grounded in real portfolio and GitHub data, session-aware conversations — two specialized modes.
$ curl -X POST /api/chat/portfolio \
-H "Content-Type: application/json" \
-d '{"message": "What are Kenneth'\''s top skills?"}'
# Response streams in real-time...
Kenneth's core expertise spans TypeScript and Node.js on the
backend, React on the frontend, PostgreSQL for data storage,
and Docker + Railway for cloud deployment...
Each mode runs its own persona, tool set, and strict scope enforcement.
Skills, experience, projects, certs, services
portfolio
POST /api/chat/portfolio
skills_listSkills, categories, and proficiency levels
experience_listWork history, projects per company, skills used
services_listDevelopment services, offerings, and pricing
projects_portfolioPortfolio projects, demos, documentation links
certificates_listProfessional certifications and courses
public_profileContact links, bio, education, achievements
receive_email_to_developerForwards user inquiries to Kenneth via email
send_email_back_to_userSends an auto-reply back to the user
pushover_notificationPush alerts to Kenneth for out-of-scope queries
Repositories, commits, branches, contributions
github
POST /api/chat/github
public_repositories_listAll public repos, sorted by last update
get_repositoryDetailed info for a specific repository
get_repository_readmeFull README content for any repo
repository_activitiesLatest 2 activities per repository
contributed_repositoriesOpen-source projects Kenneth contributed to
forked_repositoriesList of forked repositories
repository_programming_languagesLanguage breakdown per repository
get_repository_commitsTop 10 latest commits in any repo
get_repository_branchesAll branches in a repository
Architecture decisions that matter when moving beyond a demo.
Responses arrive word-by-word via chunked plain text. No buffering — the first token lands immediately.
Full conversation context persists per browser session. PostgreSQL store in production, in-memory in development.
Model-agnostic via OpenRouter. Swap any LLM by changing one environment variable — zero code changes needed.
Every answer is backed by a live API call. Up to 4 tool-call rounds per response. No hallucinations about portfolio data.
20 requests per 15 minutes per IP on the chat endpoint. Global cap of 100 req/15min with Helmet security headers.
Pino structured logging, PostHog analytics, graceful shutdown, Docker image, and a database health check endpoint.
One endpoint, two modes. Response is a plain-text stream — no JSON wrapper, no SSE framing.
| Method | Path |
|---|---|
| POST | /api/chat/portfolio |
| POST | /api/chat/github |
| GET | /api/health |
REQUEST BODY
RESPONSE HEADERS
EXAMPLE
curl
-X POST
http://localhost:5000/api/chat/portfolio
\
-H "Content-Type: application/json" \
-d '{"message": "What are Kenneth'\''s top skills?"}' \
--no-buffer
ERROR RESPONSES — application/json { message: string }
| 400 | Validation error — message missing or outside 1–2000 char range |
| 429 | Rate limit exceeded — wait 15 minutes before retrying |
| 500 | Unexpected server error |
Try the API directly — rate limited to 20 requests per 15 minutes. Conversation history persists within your browser session.
Enter to send · Shift+Enter for newline