Full-featured discussion forum modeled after phpBB: a Category → Forum → Topic → Post hierarchy, real-time chat, direct messages, moderation and an admin panel — all inside a ready-to-use Docker stack.
- Features
- Tech stack
- Design
- Prerequisites
- Installation
- Quick start
- Configuration
- Database
- Demo accounts
- Emails and notifications
- Frontend and assets
- Tests
- Code quality
- Project structure
- Roles and permissions
- License
- Hierarchical forum: categories, forums, topics and posts (same hierarchy as phpBB).
- Pagination of topics and posts (Pagerfanta).
- Rich text editor: CKEditor embedded for writing posts.
- Moderation: category/forum ordering, per-forum moderator management, member profiles.
- Admin panel: site configuration (name, description), full management of categories, forums, moderators and users.
- Members: registration, login by username, public profile, filterable member list.
- Messaging: chat with participants and direct messages.
- "Who is online": user activity over the last 5 minutes.
- Dynamic breadcrumbs depending on the page being viewed.
- Email notifications: sent asynchronously via Messenger (Doctrine).
- 100 % French interface with
fras the default locale.
| Technology | Version |
|---|---|
| PHP | 8.5 |
| Symfony | 8.1 |
| Doctrine ORM | 3.x |
| PostgreSQL | 16 |
| Nginx | 1.23 |
| Twig | 3.x |
| AssetMapper | 8.x |
| Sass (scssphp) | 0.10 |
| CKEditor (FOS) | 2.8 |
| Stimulus | 3.x |
| Pagerfanta | 4.6 |
| PHPUnit | 12 |
| PHPStan | 2.x |
SFBB re-imagines the classic bulletin board with a modern dark glassmorphism look: frosted-glass surfaces floating over a subtle aurora background, accented in indigo and violet. It ships as two distinct themes — a public theme and an admin theme.
- Isolated by design: every public rule is scoped under
.public-body(_base.scss,_layout.scss,_glass.scss) so it never leaks into the admin panel. - Design tokens — defined in
assets/styles/_tokens.scss:- Deep navy background
#0b0f1e, translucent "glass" surfaces (rgba(255,255,255,.055)) and crisp 1px borders. - Primary indigo
#818cf8, violet accent#c084fc, emerald success, amber warning and soft red danger colors. - Corner radius of
18px(12px for smaller cards),24pxbackdrop blur and layered drop shadows.
- Deep navy background
- Aurora backdrop —
_base.scss: four radial gradients (violet, blue, pink, cyan) blended over a navy linear gradient, fixed to the viewport. - Frosted glass shell —
_layout.scss: the page container usesbackdrop-filter: blur(24px) saturate(150%)over a translucent navy panel, with a solid fallback whenbackdrop-filteris not supported. - Components —
components/_glass.scss: glass cards with gradient headers, hover-highlighted rows, pill badges, uppercase micro-labels on statistics, pill-shaped pagination, tinted alerts, post cards with a side author panel and avatars with an online indicator. - Buttons —
components/_buttons.scss: indigo-to-violet gradient primary buttons with a soft glow and a subtle hover lift. - Forms —
components/_forms.scss: translucent inputs with an indigo focus ring. - Profile page —
components/_profile.scss: dotted-pattern banner, centered identity block and a 3-column statistics grid. - Icons: Font Awesome (Free); nav links collapse to icons on small screens.
- Typography: system font stack (
-apple-system, "Segoe UI", Roboto, …). - Responsive: post cards and list rows stack below
992px, the profile grid collapses below768px. - Admin theme: a separate light, clean dashboard (
admin.scss).
Captured from the dev environment (screenshots/). The Symfony dev toolbar
visible at the bottom is not present in production.
![]() |
![]() |
| Homepage: category → forum list, stats and "Who is online". | Topic list of a forum. |
![]() |
![]() |
| A topic with its posts and author panel. | The login / authentication page. |
Admin dashboard.
- Docker (20.10 or later)
- Docker Compose v2
- No local PHP installation required: all tooling runs inside the containers.
git clone git@github.com:lsoulier42/sfbb.git
cd sfbb
cp .env .env.local # optional: customize variables (see Configuration)
make installmake install runs, in order:
- the build of the Docker images (PHP 8.5, Nginx, PostgreSQL, Mailcatcher);
- the installation of Composer dependencies;
- the database migrations;
- the fixtures;
- the assets installation (importmap, Sass, CKEditor);
- the startup of the stack.
| Command | Description |
|---|---|
make start |
Starts all containers |
make stop |
Stops all containers |
make connect |
Opens a shell in the PHP container |
make install |
Build + composer install + migrations + fixtures + assets |
make composer-install |
Installs Composer dependencies |
make composer-update |
Updates Composer dependencies (-W) |
make db-migrate |
Applies migrations |
make db-fixtures |
Reloads fixtures (purge + truncate) |
make db-migrations-diff |
Generates a migration from the entities |
make db-reset |
|
make clear |
Clears the cache (run outside the container) |
make assets-install |
Installs assets (importmap) |
make assets-compile |
Compiles assets for production |
⚠️ make db-resetis destructive: it deletes all files inmigrations/, recreates the database and regenerates a full diff. Only run it when that is clearly your intent.
| Service | URL / port |
|---|---|
| Application (dev) | http://localhost:8776 |
| PostgreSQL (host) | localhost:5664 |
| Mailcatcher (UI) | http://localhost:1168 |
| Mailcatcher (SMTP) | localhost:1167 |
All environment variables are defined in .env. To customize them
without committing your changes, create a .env.local file (it is ignored by
git).
| Variable | Description | Default |
|---|---|---|
APP_ENV |
Environment (dev, prod, test) |
dev |
APP_VERSION |
Version displayed in the application | 0.1.0 |
APP_PORT |
HTTP port exposed on the host | 8776 |
APP_SECRET |
Application secret | (change in prod) |
DATABASE_USER |
PostgreSQL user | root |
DATABASE_PASSWORD |
PostgreSQL password | password |
DATABASE_NAME |
Database name | sfbb |
DATABASE_HOST |
PostgreSQL host (Docker service name) | database |
DATABASE_PORT |
PostgreSQL internal port | 5432 |
MESSENGER_TRANSPORT_DSN |
Async Messenger transport (Doctrine) | doctrine://default |
MAILER_DSN |
Mailer transport | smtp://mailer:1025 |
-
Migrations live in
migrations/. -
Generate a migration from the entities:
make db-migrations-diff
-
Apply the migrations:
make db-migrate
-
Fixtures (one class per entity in
src/DataFixtures/) create a realistic dataset: users, categories, forums, topics, posts, chats, etc.
A separate database is used in the test environment (_test suffix appended
by the when@test Doctrine configuration). No collision with your development
data.
The fixtures create the following accounts (common password: 1234test):
| Username | Role |
|---|---|
admin |
Administrator |
super-modo |
Super-moderator |
modo |
Moderator |
| (10 generated) | User |
⚠️ These accounts are for development only. Always change the default passwords in production.
- Emails are sent asynchronously via the Messenger
asynctransport (Doctrine) and processed by the Supervisor workers (mailer-messengerandfailed-messenger) inside the PHP container. - In development, all emails go through Mailcatcher (http://localhost:1168): no real email is sent.
- On failure, messages are redirected to the
failedtransport (3 attempts with backoff).
-
AssetMapper (
importmap.php) manages the JavaScript dependencies (native importmap, no bundler). -
Styles are compiled from
assets/styles/app.scssvia symfonycasts/sass-bundle. -
The JavaScript entry point is
assets/app.js. -
CKEditor is integrated through FOSCKEditorBundle; its plugins live in
public/ckeditor-plugins/. -
After any change to styles/JS:
make assets-install
-
For production, assets are compiled into
public/assets/:make assets-compile
The test infrastructure is in place (PHPUnit 12, tests/bootstrap.php) but
no tests have been written yet. To run the suite:
docker compose run --rm php bin/phpunitAdding tests (unit and functional) is welcome.
Static analysis tools run inside the Docker container:
# PHPStan — level 8 on src/ (requires a warm dev cache)
docker compose run --rm php bash -ci 'php -d memory_limit=4G bin/console cache:clear'
docker compose run --rm php bash -ci 'php -d memory_limit=4G vendor/bin/phpstan analyse -c phpstan.neon --no-progress'
# PHPCS — PSR12 on src/ and tests/
docker compose run --rm php bash -ci 'vendor/bin/phpcs --standard=phpcs.xml.dist src/ tests/'.
├── assets/ # JS (app.js) and SCSS (app.scss)
├── config/ # Symfony configuration
│ ├── packages/ # Framework, Doctrine, Security, Twig, ...
│ └── routes/ # Framework/profiler routes
├── docker/ # PHP Dockerfile, nginx and supervisord configs
├── migrations/ # Doctrine migrations
├── public/ # Web entry point + public assets (ckeditor-plugins)
├── screenshots/ # Screenshots used in this README
├── src/
│ ├── Command/ # CLI commands
│ ├── Contract/ # Service interfaces
│ ├── Controller/ # Controllers (front + admin)
│ ├── DataFixtures/ # Fixtures
│ ├── Dto/ # DTOs (forms, pagination, views)
│ ├── Entity/ # Doctrine entities
│ ├── Enum/ # Enums (roles, ordering)
│ ├── EventListener/ # Listeners (activity, login, password)
│ ├── Form/ # Form types
│ ├── Helper/ # Helpers
│ ├── Message/ # Async messages (Messenger)
│ ├── MessageHandler/ # Message handlers
│ ├── Repository/ # Repositories
│ ├── Security/ # UserChecker (login by username)
│ ├── Service/ # Business logic layer
│ ├── Traits/ # Cross-cutting traits (timestampable)
│ └── Twig/ # Twig extension
├── templates/ # Twig views
├── tests/ # Tests (PHPUnit)
├── translations/ # Translations (fr)
├── docker-compose.yaml # Docker stack (php, nginx, database, mailer)
└── Makefile # Main workflow (make install, start, ...)
| Role | Permissions |
|---|---|
ROLE_USER |
Browse, post and edit own messages |
ROLE_MODERATOR |
Basic moderation |
ROLE_SUPER_MODERATOR |
Extended moderation |
ROLE_ADMIN |
Full access to the /admin panel |
The role hierarchy (role_hierarchy) is defined in
config/packages/security.yaml. Login is
done by username (see App\Security\UserChecker).
Distributed under the MIT license.




