Secure Authentication in Java: How Not to Fail the Security Exam

Online Python Trainer for Beginners

Learn Python easily without overwhelming theory. Solve practical tasks with automatic checking, get hints in Russian, and write code directly in your browser — no installation required.

Start Course

Introduction: Why Your Password Is Not Just a String

\n\n

Imagine: you've written a cool Java application for an online library. Users register, save bookmarks, write reviews. And suddenly — a database leak. All passwords in plain text. A disaster? You bet! In 2024, data breaches occur every 39 seconds, and 81% of them are related to weak authentication. If you code in Java and want your project to stay out of cyber news headlines — this article is for you.

\n\n

We'll cover secure authentication in Java applications from A to Z: from password hashing to JWT and CSRF protection. No boring theory, only working code and real-world practices. Let's go!

\n\n

1. Password Hashing: The First Line of Defense

\n\n

The first rule of security: never store passwords in plain text. Even if your database is the holy grail, encrypting passwords is an absolute minimum. In Java, algorithms like bcrypt, scrypt, or Argon2 are used for this. Why not MD5 or SHA? Because they are too fast — an attacker can crack a password in seconds.

\n\n

Practice: bcrypt in Action

\n

Add the dependency to pom.xml (Maven):

\n
<dependency>\n    <groupId>org.springframework.security</groupId>\n    <artifactId>spring-security-crypto</artifactId>\n    <version>6.2.0</version>\n</dependency>\n
\n\n

Now hash the password during registration:

\n
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;\n\npublic class PasswordService {\n    private final BCryptPasswordEncoder encoder = new BCryptPasswordEncoder();\n\n    public String hashPassword(String rawPassword) {\n        return encoder.encode(rawPassword); // generates salt automatically\n    }\n\n    public boolean checkPassword(String rawPassword, String storedHash) {\n        return encoder.matches(rawPassword, storedHash);\n    }\n}\n
\n\n

Important: bcrypt adds a random salt automatically, so even identical passwords will look different. The default cost factor is 10, but for critical systems you can increase it to 12-14.

\n\n

2. JWT (JSON Web Tokens): Lightweight and Secure Sessions

\n\n

After registration, the user needs to somehow confirm their identity. Cookies? Possible, but JWT is the modern standard for REST APIs. The token contains user information and is signed with a secret key. No server-side sessions — everything is in the token.

\n\n

Creating JWT in Java

\n

Add the io.jsonwebtoken:jjwt library:

\n
<dependency>\n    <groupId>io.jsonwebtoken</groupId>\n    <artifactId>jjwt-api</artifactId>\n    <version>0.12.3</version>\n</dependency>\n
\n\n

Token generation:

\n
import io.jsonwebtoken.Jwts;\nimport io.jsonwebtoken.security.Keys;\nimport javax.crypto.SecretKey;\nimport java.util.Date;\n\npublic class JwtUtil {\n    private final SecretKey key = Keys.hmacShaKeyFor("secret_key_at_least_256_bits_long".getBytes());\n\n    public String generateToken(String username) {\n        return Jwts.builder()\n                .subject(username)\n                .issuedAt(new Date())\n                .expiration(new Date(System.currentTimeMillis() + 3600000)) // 1 hour\n                .signWith(key)\n                .compact();\n    }\n\n    public String extractUsername(String token) {\n        return Jwts.parser()\n                .verifyWith(key)\n                .build()\n                .parseSignedClaims(token)\n                .getPayload()\n                .getSubject();\n    }\n}\n
\n\n

Tip: don't store the secret key in code! Use environment variables or Vault. And never put sensitive data (passwords, card numbers) in JWT — the token can be decoded without the signature.

\n\n

3. CSRF Protection:

Blogs

Book Recommendations