A production-ready web application built with Spring Boot 3.5.8 featuring secure user authentication, multi-user session management, and a full-featured board system with pagination and search capabilities.
Developed as part of Java Spring course at Sungkyul University demonstrating enterprise-level web development patterns.
This is a full-stack Spring Boot application that implements:
- Secure user authentication with BCrypt password encryption
- Multi-user session management using UUID-based session tracking
- Board/Blog system with CRUD operations, pagination, and search
- File upload capabilities with configurable size limits
- Input validation using Jakarta Bean Validation
- Production-ready features including session management and security best practices
Developer: Wai Yan Naung
Framework: Spring Boot 3.5.8
Java Version: 21
Database: MySQL 8.x
- Secure user registration with encrypted password storage (BCrypt)
- Session-based authentication with UUID tracking for concurrent multi-user support
- Login/logout functionality with proper session management
- Protected routes requiring authentication before access
- Create, view, and list board posts with rich metadata
- Server-side validation for content integrity (title max 200 chars, content max 5000 chars)
- Search functionality with case-insensitive keyword filtering
- Pagination support (3 posts per page, configurable)
- Automatic date formatting (dd-MM-yyyy)
- Author name automatically assigned from logged-in user session
- Independent session management per user using UUID
- Concurrent user support without session conflicts
- Each user maintains their own authenticated session
- Secure session cookie handling with configurable timeout
- Configurable file size limits (max 10MB per file, 30MB per request)
- Static file serving for uploaded content
- Secure file storage in designated upload directory
- Layered architecture: Controller β Service β Repository
- DTO pattern for clean data transfer
- Builder pattern for entity creation
- Input validation with @Valid annotations
- Exception handling for authentication failures
- Server-side defaults for views/likes counters
| Layer | Technology |
|---|---|
| Backend | Spring Boot 3.5.8, Spring MVC, Spring Data JPA |
| Frontend | Thymeleaf, Bootstrap 4.5.2, HTML5, CSS3, JavaScript |
| Database | MySQL 8.x with JPA/Hibernate ORM |
| Security | Spring Security (BCrypt password hashing), Session Management |
| Build Tool | Maven 3.x |
| Template Engine | Thymeleaf |
| Validation | Jakarta Bean Validation API |
| Monitoring | Spring Boot Actuator |
| JS Libraries | CounterUp, Easing, Isotope, Lightbox, OwlCarousel, Typed.js, Waypoints, WOW.js |
| IDE / Tools | Visual Studio Code, Git, GitHub |
CREATE TABLE member (
id BIGINT AUTO_INCREMENT PRIMARY KEY,
name VARCHAR(255) NOT NULL,
email VARCHAR(255) UNIQUE NOT NULL,
password VARCHAR(255) NOT NULL, -- BCrypt encrypted
age VARCHAR(50) NOT NULL,
mobile VARCHAR(50) NOT NULL,
address VARCHAR(255)
);CREATE TABLE board (
id BIGINT AUTO_INCREMENT PRIMARY KEY,
title VARCHAR(200) NOT NULL,
content TEXT(5000) NOT NULL,
user VARCHAR(255) NOT NULL, -- Author name (from session)
newdate VARCHAR(50) NOT NULL, -- Format: dd-MM-yyyy
count VARCHAR(50) NOT NULL DEFAULT '0', -- View count
likec VARCHAR(50) NOT NULL DEFAULT '0', -- Like count
password VARCHAR(255) NOT NULL, -- Post password (for edit/delete)
email VARCHAR(255) NOT NULL, -- Author email
mobile VARCHAR(50) NOT NULL,
name VARCHAR(255) NOT NULL,
address VARCHAR(255),
age VARCHAR(50) NOT NULL DEFAULT '0'
);- Java JDK 21 or higher
- MySQL Server 8.x
- Maven 3.6+ (or use included
mvnw.cmd) - VS Code with Spring Boot Extension Pack (recommended)
vmware.vscode-boot-dev-pack- Spring Boot Dev Packvscjava.vscode-java-pack- Java Extension Packcweijan.vscode-mysql-client2- MySQL Clientcweijan.dbclient-jdbc- Database Client
# Clone the repository
git clone https://github.com/wynaung19/Java_Spring.git
# Navigate to project directory
cd Java_Spring- Create MySQL database:
CREATE DATABASE spring CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;- Update database credentials in
src/main/resources/application.properties:
spring.datasource.url=jdbc:mysql://localhost:3306/spring?serverTimezone=Asia/Seoul
spring.datasource.username=root
spring.datasource.password=YOUR_PASSWORD # Change this- Tables will be auto-created on first run (
spring.jpa.hibernate.ddl-auto=update)
# Windows
mvnw.cmd clean install
# Linux/Mac
./mvnw clean installOption 1: Using VS Code Spring Boot Dashboard
- Open project in VS Code
- Open Spring Boot Dashboard (left sidebar)
- Click
βΆοΈ Run button next toSkuApplication
Option 2: Using Maven Command
# Windows
mvnw.cmd spring-boot:run
# Linux/Mac
./mvnw spring-boot:runOption 3: Using Terminal
java -jar target/sku-0.0.1-SNAPSHOT.jarApplication URL: http://localhost:8080
sku/
βββ src/main/
β βββ java/com/waiyannaung/sku/
β β βββ SkuApplication.java # π Application entry point
β β βββ controller/
β β β βββ BlogController.java # π Board CRUD & pagination
β β β βββ MemberController.java # π Authentication & sessions
β β β βββ FileController.java # π File upload handling
β β β βββ BlogRestController.java # π REST API endpoints
β β β βββ SkuController.java # π§ͺ Test endpoints
β β βββ model/
β β β βββ domain/
β β β β βββ Board.java # π Board entity (JPA)
β β β β βββ Member.java # π€ Member entity (JPA)
β β β βββ repository/
β β β β βββ BoardRepository.java # ποΈ Board data access
β β β β βββ MemberRepository.java # ποΈ Member data access
β β β βββ service/
β β β βββ BlogService.java # πΌ Board business logic
β β β βββ MemberService.java # πΌ Authentication logic
β β β βββ AddArticleRequest.java # π¦ Board DTO
β β β βββ AddMemberRequest.java # π¦ Member DTO
β β βββ config/ # βοΈ Configuration classes
β βββ resources/
β βββ application.properties # βοΈ Configuration
β βββ templates/ # π¨ Thymeleaf views
β β βββ board_list.html # List with pagination
β β βββ board_view.html # Post detail view
β β βββ board_write.html # Create post form
β β βββ login.html # Login page
β β βββ join_new.html # Registration form
β β βββ join_end.html # Success page
β β βββ index.html # Homepage
β β βββ error_page/
β β βββ article_error.html # Error handling
β βββ static/ # π¨ Static resources
β βββ css/ # Bootstrap & styles
β βββ js/ # JavaScript libraries
β βββ img/ # Images
β βββ upload/ # User uploads
βββ pom.xml # π¦ Maven dependencies
βββ mvnw.cmd / mvnw # Maven wrapper
βββ README.md # π This file
| Route | Method | Description |
|---|---|---|
/ |
GET | π Homepage (portfolio) |
/member_login |
GET | π Login page |
/join_new |
GET | βοΈ Registration page |
/api/members |
POST | π User registration |
/api/login_check |
POST | β Authentication |
| Route | Method | Description |
|---|---|---|
/board_list |
GET | π List posts (paginated, searchable) |
/board_view/{id} |
GET | ποΈ View single post |
/board_write |
GET | βοΈ Create post form |
/api/boards |
POST | πΎ Submit new post |
/api/logout |
GET | πͺ Logout & clear session |
// One-way hash - cannot be decrypted
String encodedPassword = passwordEncoder.encode(rawPassword);
// Stored in DB: $2a$10$N9qo8uLOickgx2ZMRZoMye...// Each user gets unique UUID session
String sessionId = UUID.randomUUID().toString();
session.setAttribute("userId", sessionId); // Tracking ID
session.setAttribute("userName", member.getName()); // Display name
session.setAttribute("email", member.getEmail()); // Email// Redirect to login if not authenticated
if (session.getAttribute("userId") == null) {
return "redirect:/member_login";
}// Author assigned from session (prevents client manipulation)
String userName = (String) session.getAttribute("userName");
request.setUser(userName); // Not from form input- Go to http://localhost:8080/join_new
- Fill in: Name, Email, Password, Age, Mobile, Address
- Submit β Password encrypted with BCrypt
- Success page displayed
- Go to http://localhost:8080/member_login
- Enter email and password
- Session created (UUID + user info)
- Redirected to board list
- Click "κΈμ°κΈ°" (Write) button
- Login required (auto-redirect if not logged in)
- Fill form:
- Title (max 200 chars) β Required
- Password (for post security)
- Content (max 5000 chars) β Required
- Author auto-set from session
- Date auto-set (dd-MM-yyyy)
- Submit β Validated & saved
- Enter keyword β Searches titles (case-insensitive)
- Clear search β Shows all posts
- 3 posts per page
- Use numbered pagination links
- Previous/Next buttons
- Click "λ‘κ·Έμμ" button
- Session cleared
- Redirected to login
spring.datasource.url=jdbc:mysql://localhost:3306/spring?serverTimezone=Asia/Seoul
spring.datasource.username=root
spring.datasource.password=123123 # Change this
spring.jpa.hibernate.ddl-auto=update
spring.jpa.show-sql=trueserver.servlet.session.timeout=300s # 5 minutes
server.servlet.session.cookie.secure=true # HTTPS onlyspring.servlet.multipart.max-file-size=10MB
spring.servlet.multipart.max-request-size=30MB
spring.servlet.multipart.location=./src/main/resources/static/upload- β Register β Password encrypted in DB
- β Login success β Session created
- β Login fail β Error message
- β Duplicate email β Prevented
- β Logout β Session cleared
- β Create post β Author from session
- β Validation β Empty title rejected
- β Date format β dd-MM-yyyy
- β Search β Case-insensitive
- β Pagination β Works correctly
- β Protected route β Redirects to login
- β Multi-user β Independent sessions
- β Session timeout β Works as configured
MySQL connection error:
- β
MySQL running:
mysql -u root -p - β
Database exists:
CREATE DATABASE spring; - β
Credentials correct in
application.properties
Port 8080 in use:
# Windows: Kill process
netstat -ano | findstr :8080
taskkill /PID <pid> /F
# Or change port
server.port=8081Correct credentials but login fails:
- β Check PasswordEncoder bean configured
- β
Verify user in DB:
SELECT * FROM member WHERE email='test@test.com'; - β
Password should start with
$2a$or$2b$
Session lost immediately:
- β Enable cookies in browser
- β
If HTTP (not HTTPS):
server.servlet.session.cookie.secure=false
500 Error creating post:
- β
Session has
userName: Check login sets it - β All NOT NULL fields have values
- β Validation passes (title/content not blank)
Author shows UUID:
- β
Fixed: Now uses
userNamefrom session - β
Check
board_write.html:th:value="${userName}"
This project demonstrates:
- β Spring Boot 3.5.8 - Auto-configuration, starters
- β Spring MVC - Controllers, request mapping
- β Spring Data JPA - Repositories, entities, queries
- β Spring Security - BCrypt, authentication
- β Thymeleaf - Server-side templates
- β MySQL & Hibernate - ORM, database management
- β Session Management - Multi-user support with UUID
- β Input Validation - Bean Validation API
- β Layered Architecture - Controller β Service β Repository
- β DTO Pattern - Clean data transfer
- β Security Best Practices - Password hashing, session security
- Edit/delete posts with password verification
- View counter increment
- Like/unlike functionality
- Comment system
- User profile pages
- Post categories
- Rich text editor (Markdown)
- Email verification
- Password reset
- Unit & integration tests (JUnit 5)
- REST API with JWT
- Role-based access control
- Database migrations (Flyway)
- Redis session store
- Caching layer
- Docker containerization
- CI/CD pipeline