Skip to content

Repository files navigation

CMS Blog

A thoughtfully crafted editorial blog platform built with Go (hexagonal architecture) and React (Vite + TypeScript + Tailwind CSS + Framer Motion).

Features

  • Hexagonal Architecture — Clean separation of domain, ports, and adapters
  • Premium Editorial Design — Ethereal Glass (OLED #050505, glassmorphism, mesh gradients)
  • Editorial Feed — Single-column horizontal post cards à la gitlawb.com/journal
  • WYSIWYG Editor — Full-featured rich text editing (React Quill)
  • Admin Panel — Full CRUD for posts, pages, categories, tags, users
  • JWT Authentication — Role-based access (admin / editor / author)
  • Static Pages — Manageable informational pages
  • File Uploads — Image upload with date-based directory storage
  • SQLite — Zero-configuration, pure Go database (no CGO)
  • RESTful API — Clean, well-defined endpoints
  • Smooth Animations — Framer Motion + Lenis smooth scroll

Tech Stack

Backend

Dependency Purpose
Go 1.21+ Application language
julienschmidt/httprouter HTTP router
microcosm-cc/bluemonday HTML sanitization (UGCPolicy)
golang.org/x/crypto bcrypt password hashing
modernc.org/sqlite Pure Go SQLite driver (no CGO)

Frontend

Dependency Purpose
React 18 UI framework
TypeScript Type safety
Vite 5 Build tool
Tailwind CSS 3.3 Utility styling (dark mode via class strategy)
Framer Motion 10 Animations
TanStack React Query 5 Server state & caching
React Router DOM 6 Client-side routing
@phosphor-icons/react Icon set (public)
lucide-react Icon set (admin only)
React Quill 2 WYSIWYG editor
Lenis Smooth scrolling
react-markdown + rehype-highlight + remark-gfm Markdown rendering
react-hot-toast Notifications
date-fns Date formatting
Axios HTTP client

Design System

  • Vibe: Ethereal Glass — OLED black (#050505), backdrop-blur-3xl, hairline borders
  • Layout: Editorial feed in a single column (max-w-3xl mx-auto)
  • Typography: Plus Jakarta Sans (body), Playfair Display (serif), Syne (display), JetBrains Mono (code)
  • Components: Double-Bezel cards (nested shell + inner core), Button-in-Button CTAs, Fluid Island Nav
  • Motion: All animations use cubic-bezier(0.32,0.72,0,1), animate only transform/opacity
  • Breadcrumbs: Minimal /-separated mono labels in style of gitlawb.com/journal

Architecture

internal/
├── domain/           # Business entities (Post, User, Category, Tag, Page) + slug generator
├── ports/            # Interface contracts
│   ├── inbound/      # Use case interfaces
│   └── outbound/     # Repository interfaces
└── adapters/         # Concrete implementations
    ├── inbound/      # HTTP handlers + use case implementations
    │   ├── http/     # Route handlers, JWT middleware
    │   └── usecase/  # Use case logic
    └── outbound/     # SQLite repository implementations

web/frontend/src/
├── components/       # Reusable UI components (Header, Hero, PostCard, Footer, etc.)
├── pages/            # Route pages (HomePage, PostPage, PagePage, CategoryPage, etc.)
│   └── admin/        # Admin panel pages
├── lib/              # API client, utilities
├── contexts/         # Theme context
├── index.css         # Tailwind + custom styles (glass, premium, admin classes)
├── App.tsx           # Route definitions
└── main.tsx          # Bootstrap

Getting Started

Requirements

  • Go 1.21+
  • Node.js 18+
  • npm

Quick Start

# Linux / Mac
chmod +x start-dev.sh
./start-dev.sh

# Windows PowerShell
powershell -ExecutionPolicy Bypass -File .\start-dev.ps1

Manual Start

Terminal 1 — Backend:

go run ./cmd/api

Terminal 2 — Frontend:

cd web/frontend
npm run dev

Default Admin Credentials

Field Value
Email admin@example.com
Password admin123

An admin account is auto-created on first run if none exist.

Ports

Service URL
Backend API http://localhost:8080
Frontend (dev) http://localhost:3000
Uploaded files http://localhost:8080/uploads/

API Endpoints

Public

GET  /api/posts             List published posts (paginated, filterable)
GET  /api/posts/:id         Get post by ID or slug
GET  /api/pages             List published pages
GET  /api/pages/:id         Get page by ID or slug
GET  /api/categories        List categories
GET  /api/tags              List tags

Authentication

POST /api/auth/login        Login, returns JWT token

Protected (JWT required)

CRUD  /api/posts            Post management
CRUD  /api/pages            Page management
CRUD  /api/categories       Category management
CRUD  /api/tags             Tag management
CRUD  /api/users            User management
POST  /api/upload           Upload image (multipart, max 10MB)

Frontend Routes

Public:
  /                         HomePage (hero + editorial feed)
  /post/:slug               Post detail
  /page/:slug               Static page
  /category/:slug           Category filter
  /tag/:slug                Tag filter
  /search                   Search

Admin:
  /admin/login              Login
  /admin                    Dashboard
  /admin/posts              Manage posts
  /admin/posts/new          Create post
  /admin/posts/:id/edit     Edit post
  /admin/pages              Manage pages
  /admin/pages/new          Create page
  /admin/pages/:id/edit     Edit page
  /admin/categories         Manage categories
  /admin/tags               Manage tags
  /admin/users              Manage users

Configuration

Env Variable Default Description
DB_PATH ./cms.db SQLite database file path
PORT 8080 Server port
UPLOAD_DIR ./uploads File upload directory
JWT_SECRET (auto-generated) JWT signing secret

Testing

# All Go tests
go test ./...

# With coverage
go test -cover ./...

# Specific package
go test ./internal/domain/...

Project Structure

cms-blog/
├── cmd/api/             # Go entry point
├── internal/            # Go packages (hexagonal architecture)
├── migrations/          # SQL migrations (auto-run on start)
├── uploads/             # Uploaded files
├── web/
│   ├── frontend/        # React application
│   └── static/          # Fallback static assets
├── go.mod / go.sum
└── README.md

Security

  • bcrypt password hashing
  • JWT tokens (HS256, 72h expiry)
  • HTML sanitization via bluemonday UGCPolicy
  • SQL injection protection via prepared statements
  • CORS configured for dev
  • Image upload validation (types, size limit)
  • Role-based access control (admin / editor / author)

License

Educational purposes only.

About

Полнофункциональная CMS платформа для ведения блога с гексагональной архитектурой, современным фронтендом и удобной админ-панелью.

Resources

Stars

1 star

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages