A beautifully crafted, entirely static portfolio website built with pure HTML, CSS, and JavaScript — no frameworks, no build tools, no runtime server logic.
Live at: hrco.github.io
A personal portfolio and daily AI/tech digest aggregator hosted on GitHub Pages. The site features:
- Static-first architecture — everything served to users is plain HTML, CSS, and JSON
- Automated digest system — daily RSS feed aggregation via GitHub Actions
- Multi-language support — English and Slovenian with localStorage persistence
- Photography showcase — aerial drone photography with thematic galleries
- Zero dependencies — except one:
fast-xml-parserfor RSS/Atom parsing - Dark mode — retro-futuristic terminal aesthetic with smooth theme switching
hrco.github.io/
├── index.html # Homepage with digest widget
├── about_me.html # Professional profile
├── foto.html # Photo galleries (4 themed sections)
├── news.html # Digest archive listing
├── my_suggestions.html # Curated creators/resources
│
├── css/
│ └── main.css # Single stylesheet (~500 lines)
│
├── js/
│ ├── main.js # i18n, theme switching, utilities
│ ├── digest-latest.js # Fetch & render latest digest widget
│ ├── gallery.js # Photo gallery enhancements
│ └── news.js # Archive page interactions
│
├── data/ # Generated static "API"
│ ├── digest-latest.json # Latest digest payload
│ └── digest-archive.json # Index of all past digests
│
├── news/ # Generated daily digest pages
│ └── YYYY-MM-DD.html # Individual daily digest pages
│
├── images/web_1600_wm/ # Optimized photos (22 aerial images)
│
├── scripts/ # GitHub Actions automation (not served)
│ ├── daily-digest.mjs # Main digest generation script
│ └── connectors/
│ └── rss.mjs # RSS/Atom feed parser
│
├── .github/workflows/
│ └── daily-digest.yml # Scheduled automation (6:20 AM UTC daily)
│
└── .github/
└── copilot-instructions.md # AI assistant guidance
GitHub Actions (6:20 UTC daily)
↓
daily-digest.mjs
↓
Fetch RSS feeds
↓
Normalize, deduplicate, limit
↓
Generate /news/YYYY-MM-DD.html
Generate /data/digest-latest.json
Update /data/digest-archive.json
↓
git commit && git push
↓
GitHub Pages auto-deploys
↓
Browser loads homepage
↓
digest-latest.js fetches /data/digest-latest.json
↓
Renders latest digest widget
The digest aggregates from multiple sources:
// scripts/daily-digest.mjs
const FEEDS = [
"https://hnrss.org/frontpage", // HackerNews
"https://feeds.arstechnica.com/arstechnica/index", // ArsTechnica
"https://rss.nytimes.com/services/xml/rss/nyt/Technology.xml", // NY Times
"https://feeds.bloomberg.com/markets/news.rss", // Bloomberg
];To add more feeds: Edit scripts/daily-digest.mjs, update the FEEDS array, commit, and push. The workflow will use new sources on next run.
Latest digest (/data/digest-latest.json):
{
"date": "2025-12-24",
"updated_at": "2025-12-24T06:20:00.000Z",
"page": "/news/2025-12-24.html",
"count": 12,
"items": [
{
"id": "sha1-hash-of-url",
"title": "Article Title",
"url": "https://...",
"source": "example.com",
"published_at": "2025-12-24T10:30:00Z",
"summary": "Summary: Article Title"
}
]
}Archive index (/data/digest-archive.json):
{
"updated_at": "2025-12-24T06:20:00.000Z",
"days": [
{
"date": "2025-12-24",
"page": "/news/2025-12-24.html",
"teaser": "Top: Latest Article Title",
"count": 12,
"ids": ["sha1-hash-1", "sha1-hash-2", ...]
}
]
}- Node.js 20+ (for running digest scripts)
- A text editor (any will do)
- Python 3 (for local preview server)
# Clone the repository
git clone https://github.com/hrco/hrco.github.io.git
cd hrco.github.io
# Install dependencies
npm install# Start a simple HTTP server
python3 -m http.server 8000
# Open browser to http://localhost:8000# Generate today's digest
node scripts/daily-digest.mjs
# Check outputs:
# - news/YYYY-MM-DD.html (daily page)
# - data/digest-latest.json (latest payload)
# - data/digest-archive.json (archive index)# Before committing changes to automation scripts:
node scripts/daily-digest.mjs
# Verify generated files are correct
cat data/digest-latest.jsonSingle file: css/main.css (~513 lines)
- CSS Variables — Define colors, spacing, fonts once, use everywhere
- Mobile-first — Responsive grid, flexbox, modern layouts
- Theme switching —
body.theme-darkfor dark mode - Animations — Smooth transitions, hover effects, starfield background
- Typography — Orbitron (display), Work Sans (body) from Google Fonts
All theme values are CSS custom properties at the top of main.css:
:root {
--color-bg: #0a0e27;
--color-primary: #00d4ff;
--color-accent: #ff00ff;
/* ... 8+ more variables */
}Theme switching, language selection, i18n rendering:
// Change language
localStorage.setItem("language", "slo"); // or "en"
// Switch theme
cycleTheme(); // light → dark → systemFetches latest digest JSON and renders a widget on the homepage:
// Automatically runs on page load
// Fetches /data/digest-latest.json
// Renders: date, item count, archive linkMinimal JS for photo gallery scroll-snap enhancements.
Archive page interactions (if needed).
All UI text supports English and Slovenian.
-
HTML: Use
data-i18n="KEY"attribute<h1 data-i18n="MY_HEADING">Default English Text</h1>
-
JavaScript: Add to
main.jsdictionaryconst i18n = { MY_HEADING: { en: "Default English Text", sl: "Privzeto besedilo v slovenščini" } };
-
Rules:
- Always update both languages
- Slovenian copy keeps the humor
- Use consistent terminology
- Make changes locally
- Commit and push to
mainbranch - GitHub Pages auto-deploys within 30 seconds
git add .
git commit -m "Mostly harmless changes"
git push origin mainGitHub Actions has workflow_dispatch enabled. Trigger from GitHub:
- Go to Actions → Daily Digest Workflow
- Click "Run workflow" → "Run workflow" button
- Workflow executes immediately (no need to wait until 6:20 AM)
These are non-negotiable:
- Static-first — Everything served as static files
- Automation over runtime — Generate content ahead of time, not on request
- No frameworks — No React, Vue, Svelte, Astro, etc.
- No build tools — No bundlers, preprocessors, or transpilers
- Readable over clever — Code must be obvious at a glance
- Humor with discipline — Jokes welcome, chaos not
When adding new features, follow this priority:
- Can it be static? Make it static.
- Can it be generated ahead of time? Generate it.
- Can it use JSON + rendering instead of APIs? Use that.
- Must it be JavaScript? Keep it minimal and modular.
If a feature requires:
- A framework
- A backend
- A database
- User authentication
…it does not belong here.
-
Check if
/data/digest-latest.jsonexists:ls -la data/digest-latest.json
-
If missing, run digest locally:
node scripts/daily-digest.mjs
-
Check browser console for fetch errors (F12 → Console)
-
Verify file path in
js/digest-latest.jsis/data/digest-latest.json
-
Check workflow logs: Actions tab on GitHub
-
Test feed URL manually:
curl https://hnrss.org/frontpage
-
If feed is down, comment it out in
scripts/daily-digest.mjsand commit
-
Verify image files exist:
ls images/web_1600_wm/ | wc -l # Should show ~22 files
-
Check file permissions (should be readable)
-
Verify paths in HTML use forward slashes:
images/web_1600_wm/gallery_01.jpg
This site channels Douglas Adams:
- Dry, self-aware humor
- References to "Don't Panic" and cosmic indifference
- Dry observations about technology
- Witty captions that don't explain the joke
Avoid:
- Corporate marketing language
- Emojis
- Sincere self-promotion
- Explaining the joke
Simple systems last longer.
If something can be static, it probably should be. This site should be:
- Understandable in five minutes
- Still working in ten years
- Readable without documentation (but this helps)
- Maintainable by anyone comfortable with HTML/CSS/JS
Want to improve the site? Follow these steps:
- Make small, focused changes — One feature or fix per commit
- Test locally — Preview in browser, run digest script if needed
- Follow the style guide — Check agent.md for detailed guidance
- Commit with humor — Message should match site's personality
- Push to main — GitHub Pages deploys automatically
Example commits:
Mostly harmless updates to photo captions
Fix RSS feed source for Bloomberg
Add Slovenian translations for new section
Update forecast: mostly static, with occasional JavaScript
This is a personal portfolio website. Code is available for learning and inspiration. Drone photography is HRCO's original work.
Q: Why no build tools?
A: Simpler to deploy, faster to load, easier to understand, no dependency hell.
Q: Why no framework?
A: Not needed. Vanilla HTML/CSS/JS is sufficient and more maintainable.
Q: Can I add a comments section?
A: No. This is a static site. Comments require backend/database.
Q: Can I use this as a template?
A: Absolutely! It's MIT-licensed and designed to be forkable.
Q: Where's the database?
A: Git. Generated files are committed back to the repository.
Mostly harmless. 🚀