Spring Boot Backend Development Course, Spring and Spring Boot

Introduction

With the development of modern web applications, the importance of backend development is growing day by day.
The Java-based Spring framework is one of the widely used backend technologies among many developers.
In particular, Spring Boot is emerging as a tool that enables efficient development.
In this course, we will take an in-depth look at the basic concepts of the Spring framework and the characteristics and advantages of Spring Boot.

Overview of the Spring Framework

The Spring framework is an application framework for the Java platform that provides various features to conveniently assist in enterprise-level application development.
Spring is mainly composed of the following modules.

  • Spring Core: Provides the basic features of Spring, including IoC (Inversion of Control) and DI (Dependency Injection) capabilities.
  • Spring MVC: Supports the MVC architecture for web application development.
  • Spring Data: Supports integration with various databases.
  • Spring Security: Provides robust authentication and authorization features for application security.

Differences Between Spring and Spring Boot

The Spring framework has traditionally provided flexibility in application composition and management.
However, this has resulted in the need for complex configurations and initialization processes.
On the other hand, Spring Boot is a tool developed to solve these issues.
Here are the main differences between the two frameworks.

  1. Configuration Method: Spring Boot follows the principle of ‘convention over configuration,’ allowing applications to start with minimal configuration.
  2. Embedded Server: Spring Boot supports embedded web servers such as Tomcat and Jetty, allowing applications to run without separately configuring a server.
  3. Starter Dependencies: Spring Boot provides a module called ‘starter’ to easily manage various dependencies, enabling developers to easily add required features.
  4. Actuator: Spring Boot includes an actuator module that provides various features for monitoring and managing the application’s status.

Installing and Setting Up Spring Boot

To start backend development using Spring Boot, you first need to set up your development environment.
Let’s follow the steps below to install Spring Boot and create a simple project.

1. Preparing the Development Environment

The tools required to use Spring Boot are as follows.

  • Java Development Kit (JDK): Java 8 or higher is required.
  • IDE: Choose an integrated development environment (IDE) such as IntelliJ IDEA or Eclipse that supports Java development.
  • Maven/Gradle: Choose Maven or Gradle for dependency management.

2. Creating a Spring Boot Project

Spring Boot projects can be created in various ways, but the simplest way is to use Spring Initializr.
By visiting the website and entering the required settings, you can automatically generate the initial project structure.

  • Spring Initializr Website
  • Enter Project Meta Information: Set Group, Artifact, Name, Description, Package name, etc.
  • Add Required Dependencies: Choose and add Spring Web, Spring Data JPA, H2 Database, etc.
  • Download the generated project and open it in your IDE.

Structure of a Spring Boot Application

The created Spring Boot project has the following structure.

        └── src
            └── main
                ├── java
                │   └── com
                │       └── example
                │           └── demo
                │               ├── DemoApplication.java
                │               └── controller
                │                   └── HelloController.java
                └── resources
                    ├── application.properties
                    └── static
    

Creating Your First Web Application

Let’s create a simple RESTful web service.
First, we will create a controller to handle HTTP requests.

1. Creating the HelloController Class

HelloController class is the most basic class for handling web requests and can be written as follows.

        package com.example.demo.controller;

        import org.springframework.web.bind.annotation.GetMapping;
        import org.springframework.web.bind.annotation.RestController;

        @RestController
        public class HelloController {
            @GetMapping("/hello")
            public String hello() {
                return "Hello, Spring Boot!";
            }
        }
    

2. Running the Application

Running the DemoApplication class in the IDE will start the embedded server,
and when you access http://localhost:8080/hello,
you can see the message “Hello, Spring Boot!”.

Database Integration

Spring Boot supports integration with various databases.
In this section, we will build a simple CRUD application using H2 Database.

1. Adding Dependencies

Add the H2 database and JPA-related dependencies to the pom.xml file.

        
            
            
                org.springframework.boot
                spring-boot-starter-data-jpa
            
            
            
                com.h2database
                h2
                runtime
            
        
    

2. Database Configuration

Add simple configuration in the application.properties file.

        spring.h2.console.enabled=true
        spring.datasource.url=jdbc:h2:mem:testdb
        spring.datasource.driverClassName=org.h2.Driver
        spring.datasource.username=sa
        spring.datasource.password=
    

3. Creating the Entity Class

Let’s create an entity class to store data in the database.
We will create a User class to store user information.

        package com.example.demo.entity;

        import javax.persistence.Entity;
        import javax.persistence.GeneratedValue;
        import javax.persistence.GenerationType;
        import javax.persistence.Id;

        @Entity
        public class User {
            @Id
            @GeneratedValue(strategy = GenerationType.AUTO)
            private Long id;
            private String name;
            private String email;

            // Getters and Setters
        }
    

4. Creating the Repository Interface

Create a repository interface to interact with the database.

        package com.example.demo.repository;

        import com.example.demo.entity.User;
        import org.springframework.data.jpa.repository.JpaRepository;

        public interface UserRepository extends JpaRepository {
        }
    

5. Updating the Controller

To add API endpoints that handle CRUD operations,
create a UserController and add request mappings.

        package com.example.demo.controller;

        import com.example.demo.entity.User;
        import com.example.demo.repository.UserRepository;
        import org.springframework.beans.factory.annotation.Autowired;
        import org.springframework.web.bind.annotation.*;

        import java.util.List;

        @RestController
        @RequestMapping("/users")
        public class UserController {
            @Autowired
            private UserRepository userRepository;

            @GetMapping
            public List getAllUsers() {
                return userRepository.findAll();
            }

            @PostMapping
            public User createUser(@RequestBody User user) {
                return userRepository.save(user);
            }
        }
    

6. Running and Testing the Application

Restart the application, and use tools like Postman to test the
GET /users and POST /users endpoints.

Security Configuration with Spring Security

Security is very important for backend applications.
Let’s add access control and authentication through Spring Security.

1. Adding Dependencies

Add Spring Security dependency to the pom.xml file.

        
            org.springframework.boot
            spring-boot-starter-security
        
    

2. Creating the Security Configuration Class

Create a configuration class to use Spring Security.

        package com.example.demo.config;

        import org.springframework.context.annotation.Bean;
        import org.springframework.context.annotation.Configuration;
        import org.springframework.security.config.annotation.web.builders.HttpSecurity;
        import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
        import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;

        @Configuration
        @EnableWebSecurity
        public class SecurityConfig extends WebSecurityConfigurerAdapter {
            @Override
            protected void configure(HttpSecurity http) throws Exception {
                http
                    .authorizeRequests()
                    .anyRequest().authenticated()
                    .and()
                    .httpBasic();
            }
        }
    

3. Testing and Verification

Restart the application, and you can connect to API tests using HTTP Basic authentication.

Conclusion

In this course, we covered the basics of the Spring framework and the development process of
backend applications using Spring Boot.
As Spring Boot’s accessibility increases, more developers can
easily develop backend applications.
We encourage you to integrate various tools or add additional features
to create more robust applications in the future.

References

Spring Boot Backend Development Course, Implement Login and Logout with Spring Security, Membership Registration, Creating Member Domain

Hello! In this course, we will learn about backend development using Spring Boot, with a particular focus on implementing login, logout, and signup using Spring Security. This course is aimed at beginners and will cover real application development cases through practical exercises and examples. The course content generally includes the following:

  • Introduction to Spring Boot
  • Overview of Spring Security
  • Creating a member domain
  • Implementing signup functionality
  • Implementing login and logout
  • Using JWT tokens
  • Testing and conclusion

1. Introduction to Spring Boot

Spring Boot is a lightweight application framework based on the Spring Framework that helps develop applications quickly and easily. Using Spring Boot allows for simple configuration without complex XML settings, significantly contributing to productivity.

2. Overview of Spring Security

Spring Security is a framework that provides security features for Spring-based applications. It offers various functions necessary for handling authentication and authorization, helping to enhance the security of web applications.

3. Creating a member domain

To create a member domain, we first need to define the necessary entities. In this course, we will create a Member domain and set the required fields. Below is an example code of the member entity:

 
import javax.persistence.*;

@Entity
@Table(name = "members")
public class Member {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    
    @Column(nullable = false, unique = true)
    private String username;

    @Column(nullable = false)
    private String password;

    @Column(nullable = false)
    private String email;

    // Getters and Setters
}

4. Implementing signup functionality

Now, let’s implement the signup functionality. We will create a REST API to handle signup requests, allowing clients to send member information to the server. Below is the controller code for handling signup:


import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;

@RestController
@RequestMapping("/api/members")
public class MemberController {

    @Autowired
    private MemberService memberService;

    @PostMapping("/register")
    public ResponseEntity register(@RequestBody Member member) {
        memberService.register(member);
        return new ResponseEntity<>("Signup successful", HttpStatus.CREATED);
    }
}

5. Implementing login and logout

We will use Spring Security to implement the login functionality. This will allow us to handle authentication and maintain the logged-in state of users. We will add a configuration class for Spring Security:


import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;

@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {

    @Autowired
    private CustomUserDetailsService customUserDetailsService;

    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.userDetailsService(customUserDetailsService).passwordEncoder(passwordEncoder());
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http
            .csrf().disable()
            .authorizeRequests()
            .antMatchers("/api/members/register").permitAll()
            .anyRequest().authenticated()
            .and()
            .formLogin()
            .loginPage("/login")
            .permitAll()
            .and()
            .logout()
            .permitAll();
    }

    // PasswordEncoder bean configuration
}

6. Using JWT tokens

JWT (JSON Web Token) is a token used for exchanging secure information. We will generate JWT during signup and login to authenticate users. We will add code to issue JWT in this process:


import io.jsonwebtoken.Jwts;
import io.jsonwebtoken.SignatureAlgorithm;

import java.util.Date;

public class JwtUtil {

    private final String SECRET_KEY = "secret";

    public String generateToken(String username) {
        return Jwts.builder()
                .setSubject(username)
                .setIssuedAt(new Date(System.currentTimeMillis()))
                .setExpiration(new Date(System.currentTimeMillis() + 1000 * 60 * 60 * 10)) // Valid for 10 hours
                .signWith(SignatureAlgorithm.HS256, SECRET_KEY)
                .compact();
    }
}

7. Testing and conclusion

Now that all functionalities have been implemented, we will write unit tests to verify that everything works correctly. It is important to check that each feature operates as expected through testing. Below is a simple example of a unit test:


import static org.junit.jupiter.api.Assertions.*;
import org.junit.jupiter.api.Test;

public class MemberServiceTest {

    @Test
    public void testRegister() {
        Member member = new Member("testuser", "password", "test@example.com");
        memberService.register(member);
        assertNotNull(memberService.findMemberByUsername("testuser"));
    }
}

Conclusion

In this course, we explored backend development methods using Spring Boot and how to implement login, logout, and signup functionalities using Spring Security. I hope this practical experience has been helpful for you. Now, you can implement stronger user management and security features in your application.

Reference Materials

Spring Boot Backend Development Course, Implementing Login and Logout with Spring Security, Implementing Membership Registration

Introduction

Spring Boot is a powerful backend development tool based on the Spring Framework.
With Spring Boot, you can rapidly build applications and receive various features
without complex configurations. In this course, you will learn how to implement
login, logout, and sign-up features using Spring Security. This course will be
beneficial for everyone from beginners to intermediate developers.

Overview of Spring Boot and Spring Security

What is Spring Boot?

Spring Boot is a tool that helps you use the Spring Framework easily by
automatically configuring the basic settings. This allows developers to structure
their projects primarily based on annotations without complex XML configurations.
Spring Boot provides various starters that help developers easily add the libraries
and dependencies they need.

What is Spring Security?

Spring Security is a powerful and flexible authentication and authorization framework
designed for securing Spring-based applications. Through this framework, you can
easily implement login, sign-up, and authority checks in your applications.
Spring Security supports various authentication methods (e.g., form-based
login, OAuth2, etc.).

Creating a Project and Adding Dependencies

To create a Spring Boot-based project, please follow these steps.

  1. Create a new project using Spring Initializr:

    Create a Gradle-based project including Web, Spring Security, JPA, and H2 Database.

  2. Add dependencies in build.gradle:

                        dependencies {
                            implementation 'org.springframework.boot:spring-boot-starter-web'
                            implementation 'org.springframework.boot:spring-boot-starter-security'
                            implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
                            implementation 'com.h2database:h2'
                        }
                        

Implementing Sign-Up

To implement the sign-up feature, please follow these steps.

  1. Create User Entity:

                        @Entity
                        public class User {
                            @Id
                            @GeneratedValue(strategy = GenerationType.IDENTITY)
                            private Long id;
                            private String username;
                            private String password;
                            private String email;
                            // getters and setters
                        }
                        
  2. Create User Repository Interface:

                        public interface UserRepository extends JpaRepository {
                            Optional findByUsername(String username);
                        }
                        
  3. Implement Sign-Up Service:

                        @Service
                        public class UserService {
                            @Autowired
                            private UserRepository userRepository;
    
                            public void registerNewUser(User user) {
                                // Password encryption and user saving logic
                                user.setPassword(passwordEncoder.encode(user.getPassword()));
                                userRepository.save(user);
                            }
                        }
                        

Implementing Login and Logout

To implement the login and logout features, please follow these steps.

  1. Configure Spring Security:

                        @Configuration
                        @EnableWebSecurity
                        public class SecurityConfig extends WebSecurityConfigurerAdapter {
                            @Override
                            protected void configure(HttpSecurity http) throws Exception {
                                http
                                    .authorizeRequests()
                                    .antMatchers("/register").permitAll() 
                                    .anyRequest().authenticated()
                                    .and()
                                    .formLogin()
                                    .loginPage("/login")
                                    .permitAll()
                                    .and()
                                    .logout()
                                    .permitAll();
                            }
    
                            @Bean
                            public PasswordEncoder passwordEncoder() {
                                return new BCryptPasswordEncoder();
                            }
                        }
                        
  2. Implement Login and Sign-Up Controller:

                        @Controller
                        public class AuthController {
                            @Autowired
                            private UserService userService;
    
                            @GetMapping("/register")
                            public String showRegistrationForm(Model model) {
                                model.addAttribute("user", new User());
                                return "register";
                            }
    
                            @PostMapping("/register")
                            public String registerUser(@ModelAttribute User user) {
                                userService.registerNewUser(user);
                                return "redirect:/login";
                            }
    
                            @GetMapping("/login")
                            public String showLoginForm() {
                                return "login";
                            }
                        }
                        

Final Configuration and Testing

After completing the above steps, apply the following configurations and perform testing:

  1. Configuration in application.properties:

                        spring.h2.console.enabled=true
                        spring.datasource.url=jdbc:h2:mem:testdb
                        spring.datasource.driverClassName=org.h2.Driver
                        spring.datasource.username=sa
                        spring.datasource.password=password
                        
  2. Run the Application and Test:

    Run the application, attempt to sign up at /register, and then go to the /login page to test the login process.

Conclusion

So far, we have learned how to implement sign-up and login/logout procedures using
Spring Boot and Spring Security. I hope this course has helped you build a basic
authentication system. The Spring Framework is highly versatile, and you can build
even more complex systems with it. Additionally, considering further security measures
such as JWT (JSON Web Token) authentication can provide great experience.

© 2023 Spring Boot Backend Development Course

Spring Boot Backend Development Course, Implementing Login and Logout with Spring Security, User Registration, Creating User Registration and Login Views

스프링 시큐리티로 로그인/로그아웃 및 회원 가입 구현

안녕하세요! 이번 강좌에서는 스프링 부트스프링 시큐리티를 활용하여 기본적인 로그인/로그아웃 기능과 회원 가입 시스템을 구현해 보겠습니다. 이 강좌는 Java와 웹 개발에 대한 기본 지식이 있는 분들을 대상으로 하며, 실용적인 예제를 통해 배우실 수 있습니다.

1. 스프링 부트란?

스프링 부트는 스프링 프레임워크를 기반으로 한 서버측 애플리케이션 개발을 보다 간편하게 해주는 솔루션입니다. 복잡한 XML 설정을 줄이고, ‘Convention over Configuration’ 원칙을 통해 개발자가 비즈니스 로직에 집중할 수 있도록 도와줍니다. 특히, RESTful API 구축과 마이크로서비스 아키텍처에 적합하여 빠른 개발 환경을 제공합니다.

2. 스프링 시큐리티란?

스프링 시큐리티는 스프링 기반 애플리케이션을 위한 인증 및 인가 기능을 제공하는 프레임워크입니다. 유연한 보안 설정과 다양한 인증 방식을 지원하여, 애플리케이션의 보안을 강화하는 데 도움을 줍니다. 비밀번호 암호화, URL 기반 접근 제어, 사용자 역할 및 권한 관리 등의 기능을 제공합니다.

3. 프로젝트 세팅

3.1. 스프링 부트 초기화

스프링 부트 프로젝트를 생성하기 위해, Spring Initializr를 사용합니다. 필요한 의존성(Dependencies)으로는 다음과 같은 것들이 있습니다:

  • Spring Web
  • Spring Security
  • Spring Data JPA
  • H2 Database (또는 MySQL, PostgreSQL 등)
  • Spring Boot DevTools (개발 편의성 향상)

모든 의존성을 추가한 후, ZIP 파일로 프로젝트를 다운로드하고 IDE(예: IntelliJ IDEA, Eclipse)에 임포트합니다.

3.2. 디렉토리 구조 설정

기본 프로젝트 구조는 다음과 같습니다:

    src/
      └── main/
          ├── java/
          │   └── com/
          │       └── example/
          │           └── demo/
          │               ├── controller/
          │               ├── model/
          │               ├── repository/
          │               ├── security/
          │               └── service/
          └── resources/
              ├── application.properties
              └── static/
              └── templates/
    

4. 회원 가입 기능 구현

4.1. 사용자 모델 생성

회원 가입을 위해 사용자 정보를 저장할 User 엔티티 클래스를 생성합니다.

    package com.example.demo.model;

    import javax.persistence.*;
    import java.util.Collection;

    @Entity
    public class User {
        @Id
        @GeneratedValue(strategy = GenerationType.IDENTITY)
        private Long id;

        private String username;
        private String password;
        
        @ElementCollection(fetch = FetchType.EAGER)
        private Collection roles;

        // Getters and Setters
    }
    

4.2. 레포지토리 인터페이스 작성

데이터베이스와의 상호작용을 위해 레포지토리 인터페이스를 정의합니다.

    package com.example.demo.repository;

    import com.example.demo.model.User;
    import org.springframework.data.jpa.repository.JpaRepository;

    public interface UserRepository extends JpaRepository {
        User findByUsername(String username);
    }
    

4.3. 서비스 클래스 작성

유저 정보를 처리하는 서비스 클래스를 구현합니다.

    package com.example.demo.service;

    import com.example.demo.model.User;
    import com.example.demo.repository.UserRepository;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
    import org.springframework.stereotype.Service;

    @Service
    public class UserService {

        @Autowired
        private UserRepository userRepository;

        @Autowired
        private BCryptPasswordEncoder passwordEncoder;

        public void registerUser(User user) {
            user.setPassword(passwordEncoder.encode(user.getPassword()));
            userRepository.save(user);
        }

        public User findUserByUsername(String username) {
            return userRepository.findByUsername(username);
        }
    }
    

4.4. 회원 가입 컨트롤러 구현

회원 가입 요청을 처리할 컨트롤러를 만들어야 합니다.

    package com.example.demo.controller;

    import com.example.demo.model.User;
    import com.example.demo.service.UserService;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.stereotype.Controller;
    import org.springframework.ui.Model;
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.PostMapping;
    import org.springframework.web.bind.annotation.RequestMapping;

    @Controller
    @RequestMapping("/auth")
    public class AuthController {

        @Autowired
        private UserService userService;

        @GetMapping("/register")
        public String showRegistrationForm(Model model) {
            model.addAttribute("user", new User());
            return "register";
        }

        @PostMapping("/register")
        public String registerUser(User user) {
            userService.registerUser(user);
            return "redirect:/auth/login";
        }
    }
    

4.5. 뷰 템플릿 작성

회원 가입을 위한 Thymeleaf 템플릿을 작성합니다.

    <!-- src/main/resources/templates/register.html -->
    <!DOCTYPE html>
    <html xmlns:th="http://www.thymeleaf.org">
    <head>
        <title>회원 가입</title>
    </head>
    <body>
        <h1>회원 가입</h1>
        <form action="@{/auth/register}" method="post">
            <label for="username">사용자 이름:</label>
            <input type="text" id="username" name="username" required><br>
            <label for="password">비밀번호:</label>
            <input type="password" id="password" name="password" required><br>
            <button type="submit">가입</button>
        </form>
    </body>
    </html>
    

5. 로그인/로그아웃 기능 구현

5.1. 스프링 시큐리티 설정

스프링 시큐리티를 설정하기 위해 다음 클래스를 생성합니다.

    package com.example.demo.security;

    import org.springframework.context.annotation.Bean;
    import org.springframework.context.annotation.Configuration;
    import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
    import org.springframework.security.config.annotation.web.builders.HttpSecurity;
    import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
    import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
    import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
    import org.springframework.security.crypto.password.PasswordEncoder;

    @Configuration
    @EnableWebSecurity
    public class SecurityConfig extends WebSecurityConfigurerAdapter {

        @Bean
        public PasswordEncoder passwordEncoder() {
            return new BCryptPasswordEncoder();
        }

        @Override
        protected void configure(AuthenticationManagerBuilder auth) throws Exception {
            auth.userDetailsService(userDetailsService()).passwordEncoder(passwordEncoder());
        }

        @Override
        protected void configure(HttpSecurity http) throws Exception {
            http.csrf().disable()
                .authorizeRequests()
                .antMatchers("/auth/register", "/auth/login").permitAll()
                .anyRequest().authenticated()
                .and()
                .formLogin()
                .loginPage("/auth/login")
                .permitAll()
                .and()
                .logout()
                .permitAll();
        }
    }
    

5.2. 로그인 뷰 작성

로그인 페이지를 위한 Thymeleaf 템플릿을 작성합니다.

    <!-- src/main/resources/templates/login.html -->
    <!DOCTYPE html>
    <html xmlns:th="http://www.thymeleaf.org">
    <head>
        <title>로그인</title>
    </head>
    <body>
        <h1>로그인</h1>
        <form action="#" th:action="@{/login}" method="post">
            <label for="username">사용자 이름:</label>
            <input type="text" id="username" name="username" required><br>
            <label for="password">비밀번호:</label>
            <input type="password" id="password" name="password" required><br>
            <button type="submit">로그인</button>
        </form>
    </body>
    </html>
    

6. 결론

이번 강좌에서는 스프링 부트와 스프링 시큐리티를 사용하여 회원 가입 및 로그인/로그아웃 기능을 구현하는 방법에 대해 알아보았습니다. 기본적인 CRUD 기능과 RESTful API를 이해하고, 보안 기능을 추가하는 확장성 좋은 웹 애플리케이션을 만들 수 있는 기초를 쌓으셨길 바랍니다.

물론, 실전에서는 추가적인 보안 강화와 사용자 경험 향상을 위한 다양한 기능이 필요할 것입니다. 이러한 기능들을 추가하면서 더 심화된 내용을 탐구해 나가시길 바랍니다. 감사합니다!

Spring Boot Backend Development Course, Implementing Login and Logout with Spring Security, Adding Environment Variables for Testing

This course will provide a detailed explanation of how to develop a backend application using Spring Boot. The main topics include implementing user registration and login/logout features, using Spring Security, and setting up test environment variables.

1. What is Spring Boot?

Spring Boot is a tool that helps make the Spring framework easier to use, allowing for quick and easy application development. By using Spring Boot, applications can be easily run with minimal configuration, and it provides a variety of starter dependencies to enhance development convenience.

2. Introduction to Spring Security

Spring Security is a framework responsible for securing Spring-based applications. It provides authentication and authorization features to strengthen the application’s security. In this course, we will implement user registration, login, and logout through Spring Security.

3. Project Setup

To start the project, visit the Spring Boot initialization website (Spring Initializr), add the necessary dependencies, and create a new project. The following are the key dependencies to add:

  • Spring Web
  • Spring Security
  • Spring Data JPA
  • Spring Boot DevTools
  • H2 Database (used for testing)

4. Implementing User Registration Functionality

4.1. Creating the Entity Class

We will create a User entity class for the user registration functionality. This class will be used to store user information.

package com.example.demo.model;

import javax.persistence.*;

@Entity
public class User {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    
    @Column(nullable = false, unique = true)
    private String username;
    
    @Column(nullable = false)
    private String password;
    
    public User() {}
    
    public User(String username, String password) {
        this.username = username;
        this.password = password;
    }
    
    // getters and setters
}

4.2. Creating the Repository Interface

Create a JPA repository for the User entity.

package com.example.demo.repository;

import com.example.demo.model.User;
import org.springframework.data.jpa.repository.JpaRepository;

public interface UserRepository extends JpaRepository {
    User findByUsername(String username);
}

4.3. Writing the Service Class

We will create a service class to handle the business logic related to users.

package com.example.demo.service;

import com.example.demo.model.User;
import com.example.demo.repository.UserRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Service;

@Service
public class UserService {
    @Autowired
    private UserRepository userRepository;
    
    @Autowired
    private PasswordEncoder passwordEncoder;
    
    public User registerUser(String username, String password) {
        User user = new User(username, passwordEncoder.encode(password));
        return userRepository.save(user);
    }
}

4.4. Implementing the Registration API

We will implement a RESTful API to handle user requests.

package com.example.demo.controller;

import com.example.demo.model.User;
import com.example.demo.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

@RestController
@RequestMapping("/api/auth")
public class AuthController {
    @Autowired
    private UserService userService;
    
    @PostMapping("/register")
    public User register(@RequestParam String username, @RequestParam String password) {
        return userService.registerUser(username, password);
    }
}

5. Implementing Login and Logout Functionality

5.1. Configuring Spring Security

We will configure Spring Security and add a filter to handle user authentication.

package com.example.demo.config;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;

@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {
    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.inMemoryAuthentication()
            .withUser("user")
            .password(passwordEncoder().encode("password"))
            .roles("USER");
    }
    
    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.csrf().disable()
            .authorizeRequests()
            .antMatchers("/api/auth/register").permitAll()
            .anyRequest().authenticated()
            .and()
            .httpBasic();
    }
    
    @Bean
    public PasswordEncoder passwordEncoder() {
        return new BCryptPasswordEncoder();
    }
}

5.2. Implementing the Login API

The login feature will be implemented through HTTP Basic Authentication. When a user sends authentication information (username and password) to the `/api/auth/login` endpoint, Spring Security will process it.

5.3. Implementing the Logout API

Logout will be implemented by invalidating the HTTP session. When a user sends a request to the `/api/auth/logout` endpoint, the session will be invalidated.

6. Adding Environment Variables for Testing

To manage sensitive information or configurations in the testing environment, we will create an `application-test.properties` file and set the environment variables.

# application-test.properties
spring.datasource.url=jdbc:h2:mem:testdb
spring.datasource.driverClassName=org.h2.Driver
spring.datasource.username=sa
spring.datasource.password=password
spring.jpa.hibernate.ddl-auto=create-drop

7. Writing Test Cases

We will add test cases for the API using JUnit and Mockito. The test cases can be written for the UserService and AuthController.

7.1. Testing UserService

package com.example.demo.service;

import com.example.demo.model.User;
import com.example.demo.repository.UserRepository;
import org.junit.jupiter.api.Test;
import org.mockito.InjectMocks;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.autoconfigure.web.servlet.WebMvcTest;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.security.crypto.password.PasswordEncoder;

import static org.mockito.Mockito.*;

@SpringBootTest
public class UserServiceTest {
    @InjectMocks
    private UserService userService;
    
    @Mock
    private UserRepository userRepository;
    
    @Mock
    private PasswordEncoder passwordEncoder;
    
    @BeforeEach
    public void setUp() {
        MockitoAnnotations.openMocks(this);
    }
    
    @Test
    public void testRegisterUser() {
        when(passwordEncoder.encode("password")).thenReturn("encodedPassword");
        when(userRepository.save(any(User.class))).thenReturn(new User("username", "encodedPassword"));
        
        User user = userService.registerUser("username", "password");
        
        assertEquals("username", user.getUsername());
        verify(userRepository).save(any(User.class));
    }
}

8. Conclusion

In this course, we learned how to apply Spring Security for user registration, login, and logout functionality in a backend application based on Spring Boot. We also explored how to add test environment variables and write test cases to improve the application’s quality. Based on this foundation, we encourage you to add more complex features and apply them in real-world projects.

9. References